指针和字符串(待续)

本文详细介绍了C语言中的一级指针、指针与数组的关系、const关键字在指针中的应用,以及字符串的定义、特点和相关操作。通过示例展示了如何使用指针进行函数参数传递,数组和指针的转换,以及如何进行字符串的比较、复制和连接等操作。同时,文章还讨论了const指针和常量指针的区别。
摘要由CSDN通过智能技术生成

一、指针

1.一级指针:

通常用作函数的输入参数,因为一级指针作为函数参数,在调用的时候,实参和形参是不同的内存空间,只是,这个内存空间存放的指针指向的是同一块地址 ,所以形参在函数执行中可以访问实参指向的内存空间,但是形参的指向的改变并不能影响实参。

一级指针做函数参数, 在函数内做形参做重新指向并 不会影响实参的指向。

//一级指针的应用

void Swap(int* p,int* q) 
{
	int temp = *p; //a
	*p = *q;
	*q = temp;	
}
int main()
{	
int a = 10;
int b = 20;
Swap(&a, &b);  // 栈帧 开辟  回退问题 -> 函数调用
printf("交换后的值:%d %d\n", a, b);
}

2.指针和数组的关系

int CicleNum(int* arr,int len) 
{
	assert(arr != NULL);
	int left = len;// 剩余的人数
	int count = 0;//  报数  NUM  退出
	int res = -1;// 返回剩余一个人的编号
	for (int i = 0;left > 1; i = ++i % len)
	{
		if (*(arr+i) != -1) {  //arr[i]
			count++;
		}
		if (count == NUM) {  // 报数为NUM的人退出
			*(arr + i) = -1;
			count = 0;
			left--;
		}
	}
	for (int i = 0; i < len; i++) {
		if (*(arr + i) != -1) {
			res = *(arr + i);//arr[i]
		}
	}
	return res;
}

int main()
{
	Money(85);
	int arr[] = {1,2,3,4,5,6,7,8,9,10}; 
	printf("%d  ",CicleNum(arr, 10));
}



数组和指针关系:(p+i) <==> &p[i]
      const char *str = "hello"; 
     *(str+i) = 'z';//error
     *(str+i)  -> str[i]
 
      char arr[] = "hello";
*     arr[0] = 'z';//right

数组arr[]在 CicleNum()中退化为指针*arr

(1)数组:数组是用于储存多个相同类型数据的集合。

(2)指针:指针相当于一个变量,但是它和不同变量不一样,它存放的是其它变量在内存中的地址

区别:

1)同类型指针变量可以相互赋值,数组不行,只能一个一个元素的赋值或拷贝;

2)数组在内存中是连续存放的,开辟一块连续的内存空间。数组是根据数组的下进行访问的,多维数组在内存中是按照一维数组存储的,只是在逻辑上是多维的;

3)指针可以指向任意类型的数据。指针的类型说明了它所指向地址空间的内存。

3.const和指针结合

1. 指针 和 const的使用
 1)  
	int a = 10;
	int b = 20;
	const int* p = &a;   -> 不能修改指向变量的值
	*p = 100;//error
	p = &b; //right
	*p = 200;//error 
 
 2) 
	int a = 10,b=20;
	int*  const p = &a;   
		-> 修饰指针变量本身。一经指向a,不能指向其他地址。 
			没有限定a本身的值是否被修改
	p = &b;//error
	*p = 100;//right

 3)
   const int a = 10; // a常变量
   int* p = &a;  //error    *p = 10;  error
   const int* p = &a;//right
 
 4)
  const int* const p = &a;  // p指向a,不能指向其他变量。p不能修改a的值

4.字符串的定义和特点


  1) char ch[] = "hello"; //"hello"以字符数组的形式存储 数组大小5+1 '\0'
  2) char *p = "hello"; //字符串常量"hello"  //error
     const char* str = "hello";   //right
  3)char str[5];
        scanf(“%s”,str); 
  4)char str[5];gets(str); 

5.字符串相关的操作

strcpy(p, p1) 复制字符串 
strncpy(p, p1, n) 复制指定长度字符串 
strcat(p, p1) 附加字符串 
strncat(p, p1, n) 附加指定长度字符串 
strlen(p) 取字符串长度 
strcmp(p, p1) 比较字符串 
strcasecmp忽略大小写比较字符串
strncmp(p, p1, n) 比较指定长度字符串 
strchr(p, c) 在字符串中查找指定字符 
strrchr(p, c) 在字符串中反向查找 
strstr(p, p1) 查找字符串 
strpbrk(p, p1) 以目标字符串的所有字符作为集合,在当前字符串查找该集合的任一元素 
strspn(p, p1) 以目标字符串的所有字符作为集合,在当前字符串查找不属于该集合的任一元素的偏移 
strcspn(p, p1) 以目标字符串的所有字符作为集合,在当前字符串查找属于该集合的任一元素的偏移  
* 具有指定长度的字符串处理函数在已处理的字符串之后填补零结尾符 

(1)strlen(p) 取字符串长度

字符串基本认识
int main()
{
	char ch[] = {'h','e','l','l','o'}; //5
	char arr[] = "he\0llo"; //7  字符串'\0' 结尾标记
	arr[0] = 's';
	int len_ch = sizeof(ch) / sizeof(ch[0]);
	int len_arr = sizeof(arr) / sizeof(arr[0]);

	int len_string = strlen(arr); //第一个'\0'前面字符个数
	//2个
	printf("ch:%d   arr:%d   字符串长度%d\n",len_ch,len_arr,len_string);
	return 0;


char arr[] = {'h','e','l','l','o'};
* arr -> sizeof(arr)/sizeof(arr[0]);   //5 
* strlen(arr);  //5

(2)strcmp(p, p1) 比较字符串 

        strcmp(const char*str1,const char*str2);  //比较大小功能

// 方法一: 采用数组形式操作  -》 需要优化
int my_strcmp1(const char* str1,const char* str2) {
    assert(str1!=NULL && str2 != NULL);
    int len = strlen(str1);
    for (int i = 0; i <= len; i++) {
        if (str1[i] == str2[i]) {
            continue;
        }
        else if (str1[i] > str2[i]) {
            return 1;
        }
        else {
            return -1;
        }
    }
    return 0;
}

int my_strcmp1(const char* str1, const char* str2) {
    assert(str1 != NULL && str2 != NULL);
    int result = 0; 
    int len = strlen(str1);
    for (int i = 0;i <= len ; i++) {
        if (str1[i] == str2[i]) {
            continue;
        }
        else {
            result = str1[i] > str2[i] ? 1 : -1;
            break;
        }
    }
    return 0;
}

//方法二:指针形式操作:   
int my_strcmp1(const char* str1, const char* str2) {
    assert(str1 != NULL && str2 != NULL);
    int i = 0;
    while (*str1 == *str2) { //abc       abc
        if (*str1 == '\0' && *str2 == '\0') {
            return 0;
        }
        str1++;
        str2++;
    }
    return *str1 > *str2 ? 1 : -1;
}

int main()
{
    const char* str1 = "abc";
    const char* str2 = "abg";
    int num = my_strcmp1(str1,str2);
    printf("%d",num);
    return 0;
}

(3)tstrcat(p, p1) 附加字符串(连接字符串)

char* my_strcat(char* str1, const char* str2) {
    assert(str1!=NULL && str2!=NULL);
    int len = strlen(str1);
    // 给str1后连接str2数据
    int i = 0;
    for (;i < strlen(str2); i++) {
        str1[len+i] = str2[i];
    }
    str1[len+i] = '\0'; // 字符串结尾标记'\0'
    return str1;
}

int main()
{
    char ch[10] = "abc";//'\0'
    char *res = my_strcat(ch, "def"); //abcdef
    strcat(char*str1,const char*str2)
    printf("%s",res);
    return 0;
}

(4)strcpy(p, p1) 复制字符串 

char* my_strcpy(char* str1, const char* str2) {
    assert(str1 != NULL && str2 != NULL);
    //指针实现方式:
    while (*str2!='\0') { //abc\0     abc
        *str1 = *str2;
        str1++;
        str2++;
    }
    *str1 = '\0';
    return str1;  

int main()
{
   char str1[10] = "abc";
   const char* str2 = "defghi";
   char* res = my_strcpy(str1, str2);
   printf("%s",res);

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值