strcpy与strncpy的区别


1.strcpy的隐患:

  • strcpy(char *to,const char *from);
  • 该函数判断’\0’作为结束条件,如果目标字符串to的 空间不足 ,则会 发生溢出 。这是一个潜在的安全隐患,随时有可能会出现错误。

2.strncopy的安全性:

  • strncpy(char *to,const char *from,int size);
  • strncpy通过size来控制复制的结束,这个size是要从源字符串from的大小(size <= sizeof(to)-1),这便保证了字符复制的安全性。这是一种强制性的安全措施,同样它有似乎不可避免的会产生下面的问题:
    • 1.strncpy不能保证目标字符串to以’\0’结尾。
      这种情况发生在源字符串from长度大于目标字符串to的长度。
    • 2.源字符串from较小,而目标字符串to较大,将会用大量’\0’填充剩余的空间。
   另一本版, size =sizeof(to)-1,感觉这一解释更合理

1 C 库函数 - strcpy()

C 标准库 - <string.h>

描述
C 库函数 char *strcpy(char *dest, const char *src) 把 src 所指向的字符串复制到 dest。

需要注意的是如果目标数组 dest 不够大,而源字符串的长度又太长,可能会造成缓冲溢出的情况。

声明
下面是 strcpy() 函数的声明。
char *strcpy(char *dest, const char *src)

参数
dest – 指向用于存储复制内容的目标数组。
src – 要复制的字符串。

返回值
该函数返回一个指向最终的目标字符串 dest 的指针。

实例
下面的实例演示了 strcpy() 函数的用法。

实例 1
#include <stdio.h>
#include <string.h>
 
int main()
{
   char src[40];
   char dest[100];
  
   memset(dest, '\0', sizeof(dest));//使用函数 memset() 来清除内存位置。
   strcpy(src, "This is runoob.com");
   strcpy(dest, src);
 
   printf("最终的目标字符串: %s\n", dest);
   
   return(0);
}

让我们编译并运行上面的程序,这将产生以下结果:

最终的目标字符串: This is runoob.com

实例 2
需要注意的是如果目标数组 dest 不够大,而源字符串的长度又太长,可能会造成缓冲溢出的情况。
在这里插入图片描述

实例 3

#include <stdio.h>
#include <string.h>
 
int main ()
{
  char str1[]="Sample string";
  char str2[40];
  char str3[40];
  strcpy (str2,str1);
  strcpy (str3,"copy successful");
  printf ("str1: %s\nstr2: %s\nstr3: %s\n",str1,str2,str3);
  return 0;
}

让我们编译并运行上面的程序,这将产生以下结果:

str1: Sample string
str2: Sample string
str3: copy successful

2 C 库函数 - strncpy() (字符串限长复制)

C 标准库 - <string.h>
描述
C 库函数 char *strncpy(char *dest, const char *src, size_t n) 把 src 所指向的字符串复制到 dest,最多复制 n 个字符。当 src 的长度小于 n 时,dest 的剩余部分将用空字节填充。

参数
dest – 指向用于存储复制内容的目标数组。
src – 要复制的字符串。
n – 要从源中复制的字符数。

返回值
该函数返回最终复制的字符串。

实例
下面的实例演示了 strncpy() 函数的用法。在这里,我们使用函数 memset() 来清除内存位置。

#include <stdio.h>
#include <string.h>
 
int main()
{
   char src[40];
   char dest[12];
  
   memset(dest, '\0', sizeof(dest));//使用函数 memset() 来清除内存位置。
   strcpy(src, "This is runoob.com");
   strncpy(dest, src, 10);
 
   printf("最终的目标字符串: %s\n", dest);
   
   return(0);
}

让我们编译并运行上面的程序,这将产生以下结果:

最终的目标字符串: This is ru

3 strcpy(str, p)

char str[4] = { 0 };
char* p = "abc";
strcpy(str, p);
printf("%s\n",str);

在这里插入图片描述

如果,str的空间 小于 p指向的串;
虽然拷贝过来了,但程序崩溃

    char str[4] = { 0 };
	char* p = "abcefgh";
	strcpy(str, p);

在这里插入图片描述

4 strncpy(str, p, sizeof(str) - 1)

函数原型:char *strncpy(char *dest, char *src, size_t num);

	char str[4] = { 0 };
	char* p = "abcefgh";
	strncpy(str,p,sizeof(str)-1);

当改用strncpy()后,指定了拷贝长度为 str空间 - 1 ,减1是因为str最后一个空间存储的是结束符 ‘\0’
在这里插入图片描述

strncpy遇到’\0’就结束了,不会在拷贝’\0’后面的字符;
而strcpy会在拷贝’\0’;

下面例子 在p串中加入 ‘\0’,
strncpy并没有拷贝串后的\0字符。
两者都不能越界拷贝。只要正确使用strncpy, 那就比strcpy安全。

	char str[4] = { 0 };
	char* p = "a\0bcefgh";
	strncpy(str,p,sizeof(str)-1);

在这里插入图片描述

在这里插入图片描述

strnpy拷贝的是字符串,会拷贝最后一个\0;
strncpy拷贝的是字符,不拷贝串,所以最后一个\0没有拷贝;

	char str[4] = { 0 };
	str[3] = 'w'; //故意将最后的\0换成w
	char* p = "abc";
	strcpy(str, p);//虽然字符串str最后一个位置的结束符被置为'w',但在拷贝p时,拷贝了"abc",还拷贝了最后一个结束符'/0'

在这里插入图片描述

  char str[4] = "xyz";
	str[3] = 'w'; //故意将最后的\0换成w
	char* p = "abc";
	//strcpy(str, p);
	strncpy(str,p,sizeof(str)-1);
	//strncpy拷贝的是字符,最后一个\0没有拷贝;str[3]的位置是'w',而不是结束符

在这里插入图片描述

  • 2
    点赞
  • 22
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

R-G-B

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值