零基础入门学习C语言009讲:指针(5)

版权声明:转载请标明出处 https://blog.csdn.net/qq_41556318/article/details/89737039

今天我们继续来学习字符指针作函数参数的用法,首先,在上一个博客里,有一个小问题,不知道大家找到答案没?

#include <stdio.h>
 
void  main()
{
	void copy_string(char *from, char *to);
 
	char *a = "I am a teacher.";
	char *b = "You are a student.";
 
	printf("String a = %s\nString b = %s\n", a, b);
	printf("copy string a to string b:\n");
 
	copy_string(a, b);
 
	printf("\nString a = %s\nString b = %s\n", a, b);
}
 
void  copy_string(char *from, char *to)
{
	for (; *from != '\0'; from++, to++)
	{
		*to = *from;
	}
 
	*to = '\0';
}
 
//丫的,出错了,为什么? WHY??

但是,如果我们把第6行代码改一下:char b[] = "You are a student.";,这段代码就可以正确运行了,这是为什么呢?

因为这里是copy a 到b,a没有被写,而b需要被写,所以b不能为*b。

大家就会纳闷了。

a是一个指针变量来存放字符串,b使用一个数组变量来存放字符串,它们都是来存放一个字符串,为什么就会产生如此大的区别。

我们知道C语言是存在五大内存分区的,当我们定义一个字符串时,默认是把该字符串放在常量存储区的,该存储区里面存放的都是常量,是不允许修改的。

如果我们使用一个指针指向这个常量的话(如*a),在之前,我们使用*b指向需要被修改的字符串,就会报错。

接下来,我们优化:对 copy_string 函数还可作简化

方法一

#include <stdio.h>

void  main()
{
      void copy_string( char *from, char *to );

      char *a = "I am a teacher.";
      char b[] = "You are a student.";

      printf("String a = %s\nString b = %s\n", a, b);
      printf("copy string a to string b:\n");

      copy_string(a, b);
 
      printf("\nString a = %s\nString b = %s\n", a, b);
}

void  copy_string( char *from, char *to )
{
      while( (*to = *from) != '\0' )
      {
            to++;
            from++;
      }
}

方法二

#include <stdio.h>

void  main()
{
      void copy_string( char *from, char *to );

      char *a = "I am a teacher.";
      char b[] = "You are a student.";

      printf("String a = %s\nString b = %s\n", a, b);
      printf("copy string a to string b:\n");

      copy_string(a, b);
 
      printf("\nString a = %s\nString b = %s\n", a, b);
}

void  copy_string( char *from, char *to )
{
      while( (*to++ = *from++) != '\0')
      {
            ;
      }
}

方法三

#include <stdio.h>

void  main()
{
      void copy_string( char *from, char *to );

      char *a = "I am a teacher.";
      char b[] = "You are a student.";

      printf("String a = %s\nString b = %s\n", a, b);
      printf("copy string a to string b:\n");

      copy_string(a, b);
 
      printf("\nString a = %s\nString b = %s\n", a, b);
}

void  copy_string( char *from, char *to )
{
      while( *from != '\0' )
      {
            *to++ = *from++;
      }
      *to = '\0';
}

方法四

#include <stdio.h>

void  main()
{
      void copy_string( char *from, char *to );

      char *a = "I am a teacher.";
      char b[] = "You are a student.";

      printf("String a = %s\nString b = %s\n", a, b);
      printf("copy string a to string b:\n");

      copy_string(a, b);
 
      printf("\nString a = %s\nString b = %s\n", a, b);
}

void  copy_string( char *from, char *to )
{
      while( *to++ = *from++ )
      {
            ;    // '\0' == 0  结束标志'\0'就是循环的结束标志
      }
}

方法五

#include <stdio.h>

void  main()
{
      void copy_string( char *from, char *to );

      char *a = "I am a teacher.";
      char b[] = "You are a student.";

      printf("String a = %s\nString b = %s\n", a, b);
      printf("copy string a to string b:\n");

      copy_string(a, b);
 
      printf("\nString a = %s\nString b = %s\n", a, b);
}

void  copy_string( char *from, char *to )
{
      for( ; *to++ = *from++; )
      {
            ;
      }
}

方法六

#include <stdio.h>

void  main()
{
      void copy_string( char *from, char *to );

      char *a = "I am a teacher.";
      char b[] = "You are a student.";

      printf("String a = %s\nString b = %s\n", a, b);
      printf("copy string a to string b:\n");

      copy_string(a, b);
 
      printf("\nString a = %s\nString b = %s\n", a, b);
}

void  copy_string( char from[], char to[] )
{
      char *p1, *p2;
      
      p1 = from;
      p2 = to;

      while( (*p2++ = *p1++) != '\0' )
      {
            ;
      }
}

对使用字符指针变量和字符数组的讨论

虽然用字符数组和字符指针变量都能实现字符串的存储和运算,但它们二者之间是有区别的,不应混为一谈……

主要概括起来有以下几点:

1. 字符数组由若干个元素组成,每个元素中  放一个字符,而字符指针变量中存放的是地址(字符串第1个字符的地址),决不是将字符串放到字符指针变量中。

2. 赋值方式。对字符数组只能对各个元素赋值,不能用以下办法对字符数组赋值。

     char  str[20];

     str=″I love Fishc.com!″;

  而对字符指针变量,可以采用下面方法赋值:

     char  *a;

     a=″I love Fishc.com!″;

  但注意赋给a的不是字符,而是字符串第一个 元素的地址。

3. 对字符指针变量赋初值:

char *a=″I love Fishc.com!″;

等价于

char  *a;

a=″I love Fishc.com!″;

而对数组的初始化:

char str[20]={″I love Fishc.com!″};

不能等价于

char str[20];

str[ ]=″I love Fishc.com!″;

4. 如果定义了一个字符数组,在编译时为它分配内存单元,它有确定的地址。而定义一个字符指针变量时,给指针变量分配内存单元,在其中可以放一个字符变量的地址也就是说,该指针变量可以指向一个字符型数据,但如果未对它赋予一个地址值,则它并未具体指向一个确定的字符数据。 

我们举个例子来说明

如:  

char str[10];

scanf(″%s″,str);

以上是完全可以的!

而常有人用下面的方法,目的是想输入一个字符串,虽然一般也能运行,但这种方法是危险的 :

char *a;

scanf(″%s″,a);

5. 指针变量的值是可以改变的,如:

//改变指针变量的值

#include <stdio.h>

void main()
{
	char *a = "I love www.csdn.net!";
	printf("%s\n", a);

	a += 7;
	printf("%s\n", a);
}

另外需要说明的是,若定义了一个指针变量,并使它指向一个字符串,就可以用下标形式引用指针变量所指的字符串中的字符。

//下标形式引用指针变量

#include <stdio.h>
void main()
{
	char *a = "I love www.csdn.net!";
	int i;

	printf("The sixth character is %c\n\n", a[5]);

	for (i = 0; a[i] != '\0'; i++)
	{
		printf("%c", a[i]);
	}

	printf("\n");
}

 

猜你喜欢

转载自blog.csdn.net/qq_41556318/article/details/89737039