自己实现(strlen,strcpy,strncpy,strcmp,strncmp,strcat,strncat)

本文提供了一系列C++中实现的字符串操作函数,包括计算长度、复制、连接、比较等基本功能,并附带了详细的代码实现。

废话不多说,直接上代码,能看懂看,看不懂别看了,学习这种事,随缘就好

#include<iostream>
#include<assert.h>
using namespace std;
size_t my_strlen(const char *str)
{
	assert(str != NULL);
	if(*str == '\0')
		return 0;
	else
		return my_strlen(str+1) + 1;
}

char* my_strcpy(char *strDest, const char *strSrc)
{
	char *start = strDest;           
    assert(strDest != NULL&&strDest != NULL);  
	char *ptmp_Dest = strDest;
	const char *ptmp_Src = strSrc;
    while (*ptmp_Src != '\0')   
    {  
        *ptmp_Dest++ = *ptmp_Src++;  
    }  
	*ptmp_Dest = '\0';
    return start;        
	
}
char *my_strncpy(char *dst, const char *src, size_t n)  
{  
    char *start = dst;         
    assert(dst != NULL&&src != NULL);        
    while (n--)                
    {  
        if (*src == '\0')      
        {  
            *dst = '\0';  
            dst++;  
        }  
        else  
        {  
            *dst = *src;  
            dst++;  
            (char*)src++;  
        }  
    }   
    return start;       
}  

//str1 > str2  : 1
//str1 == str2 : 0
//str1 < str2  : -1
int my_strcmp(const char *str1, const char *str2)
{
	assert(str1!=NULL && str2!=NULL);
	if(*str1=='\0' && *str2=='\0')
		return 0;
	while(*str1!='\0' && *str2!='\0')
	{
		if(*str1 > *str2)
			return 1;
		else if(*str1 < *str2)
			return -1;
		else
		{
			str1++;
			str2++;
		}
	}
	if(*str1=='\0' && *str2!='\0')
		return -1;
	else if(*str1!='\0' && *str2=='\0')
		return 1;
	return 0;
}
int my_strncmp(const char *str1, const char *str2, size_t n)  
{  
    assert(str1 != NULL&&str2 != NULL);  
    while (n && (*str1 == *str2))  
    {  
        (char*)str1++;  
        (char*)str2++;  
        n--;  
    }  
    if (n > 0)  
        return *str1 - *str2;  
    return *(str1-1) - *(str2-1);  
}  

char* my_strcat(char *strDest, const char *strSrc)
{					
	assert(strDest!=NULL && strSrc!=NULL);
	char *ptmp_Dest = strDest;
	const char *ptmp_Src = strSrc;
	while(*ptmp_Dest != '\0')
		++ptmp_Dest;
	while(*ptmp_Src != '\0')
		*ptmp_Dest++ = *ptmp_Src++;
	*ptmp_Dest = '\0';
	return strDest;
}
char *my_strncat(char *dst, const char *src, size_t n)  
{  
    char *start = dst;  
    assert(dst != NULL&&src != NULL);   
    while (*dst)    
        dst++;   
    while (n--)    
        *dst++ = *(char*)src++;    
    return start;  
}  

<think>好的,我现在需要回答用户关于C语言中strcpystrcmpstrcat和sprintf函数的用法及区别的问题。首先,我得回忆这些函数的基本功能,并确保自己理解正确。用户还提供了三个引用,可能需要参考这些内容,但根据系统指令,用户不可见这些引用,所以我只需要根据已知知识回答,但可能在引用部分末尾添加标识。 首先,逐个分析每个函数: 1. **strcpy**:用于字符串复制。用户提供的引用[1]中提到了strncpy,但用户问的是strcpystrcpy将源字符串复制到目标,包括终止符,但需要注意目标缓冲区足够大,否则可能溢出。引用[1]中的示例代码用了strcpystrncpy,可能可以用来对比说明strcpy的安全性隐患,从而引出strncpy的优势。 2. **strcmp**:字符串比较。引用[2]中提到了strcmpstrncmp的应用,用户的问题也提到了strcmp。需要解释其返回值(0表示相等,正负数表示字典序差异),并举例说明如何比较两个字符串是否相等。可能提到引用[2]中的例子,计算子串出现次数,其中用到了strncmp,但用户的问题中strcmp是直接比较整个字符串。 3. **strcat**:字符串连接。将源字符串追加到目标末尾,同样需要注意目标缓冲区大小,避免溢出。引用[3]中提到了strcat,可能需要说明其与strcpy的不同之处在于追加而不是覆盖。 4. **sprintf**:格式化输出到字符串。这个函数功能更复杂,可以将多种类型的数据格式化成字符串,类似于printf,但输出到字符数组中。需要强调其与前三者的不同,比如处理多种数据类型和格式控制,同时也要注意缓冲区溢出问题。 接下来,需要整理这四个函数的区别,包括功能、参数、返回值以及安全注意事项。例如,strcpystrcat可能存在安全隐患,因为它们不检查目标缓冲区大小,而strncpystrncat等更安全的版本可以指定最大长度。同时,sprintf也有相关的安全版本,如snprintf。 用户提供的引用中提到了strncpystrcmp的应用,可能需要在回答中引用这些例子来说明安全函数的使用,比如引用[1]中的strncpy和引用[2]中的strncmp。但根据系统指令,引用标识需要自然地添加在段落末尾,例如在讨论strncpy时引用[^1],或者在讨论子串比较时引用[^2]。 另外,需要确保回答符合格式要求:行内数学表达式用$...$,独立公式用$$...$$,但问题中可能较少涉及数学公式,但如果有的话需要正确应用。例如,在解释字符串长度时可能需要提到strlen函数返回的长度为$n$,其中不包括终止符。 然后生成相关问题,可能涉及这些函数的安全替代、使用场景、常见错误等。例如,如何避免缓冲区溢出,或者这些函数在字符串处理中的典型应用案例。 最后,检查回答是否符合中文回答,结构清晰,并正确引用参考。确保没有使用Markdown格式,代码块用三个反引号包裹,并正确标注引用标识。</think>### C语言字符串处理函数详解 #### 一、函数用法及特性对比 1. **strcpy** - **功能**:将源字符串(包括终止符`\0`)复制到目标缓冲区。 - **语法**:`char *strcpy(char *dest, const char *src);` - **示例**: ```c char dest[20]; strcpy(dest, "hello"); // dest内容变为"hello\0" ``` - **风险**:若`dest`空间不足,会导致缓冲区溢出。 2. **strcmp** - **功能**:按字典序比较两个字符串。 - **返回值**: - `0`:字符串相等 - `>0`:`str1`大于`str2` - `<0`:`str1`小于`str2` - **语法**:`int strcmp(const char *str1, const char *str2);` - **示例**: ```c if (strcmp(str1, "target") == 0) { // 字符串相等时的操作 } ``` 3. **strcat** - **功能**:将源字符串追加到目标字符串末尾。 - **语法**:`char *strcat(char *dest, const char *src);` - **示例**: ```c char dest[20] = "hello"; strcat(dest, " world"); // dest变为"hello world\0" ``` - **风险**:需确保`dest`剩余空间足够容纳`src`内容[^3]。 4. **sprintf** - **功能**:格式化数据写入字符串,支持多种数据类型(如整数、浮点数)。 - **语法**:`int sprintf(char *str, const char *format, ...);` - **示例**: ```c char buffer[50]; int num = 42; sprintf(buffer, "Value: %d", num); // buffer内容为"Value: 42\0" ``` - **风险**:格式化字符串过长可能导致溢出,建议使用`snprintf`[^3]。 --- #### 二、核心区别总结 | 函数 | 功能 | 安全性隐患 | 适用场景 | |----------|----------------|------------------|------------------------------| | `strcpy` | 字符串复制 | 缓冲区溢出 | 已知目标空间足够时 | | `strcmp` | 字符串比较 | 无 | 判断字符串相等或排序 | | `strcat` | 字符串拼接 | 缓冲区溢出 | 动态构建字符串 | | `sprintf`| 格式化字符串 | 格式错误或溢出 | 复杂数据转换为字符串 | --- #### 三、安全替代方案 - **strncpy**:限定复制的最大长度(见引用[^1]示例)。 - **strncat**:限定追加的字符数。 - **snprintf**:限定输出的字符总数,避免溢出。 ---
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值