【C语言进阶】-3-字符函数和字符串函数

point

库函数介绍

strlen↓

 size_t strlen(const char* str);
  • 参数(str):
  • 参数指向的字符串必须要以 ‘\0’ 结束。
  • 返回值(size_t):
  • 注意函数的返回值为size_t,是无符号的( 易错 )
  • strlen函数返回的是在字符串中 ‘\0’ 前面出现的字符个数(不包含 ‘\0’ )。
#include <string.h>
int main()
{
	char arr1[] = "hello";
	char arr2[] = { 'a','b','c' };
	printf("%llu\n", strlen(arr1));
	printf("%llu\n", strlen(arr1+1));
	printf("%llu\n", strlen(arr2));
	return 0;
}

在这里插入图片描述
在这里插入图片描述

🐖%llu→打印64位无符号整型
在这里插入图片描述

strcpy↓

char* strcpy(char* destination, const char* source);
  • 参数:
  • 源字符串(source)必须以 ‘\0’ 结束;
  • 会将源字符串(source)中的 ‘\0’ 拷贝到目标空间(desitination);
  • 目标空间必须足够大,以确保能存放源字符串;
  • 目标空间必须可变.
  • 返回值(size_t):
  • return destination

在这里插入图片描述

/* strcpy example */
#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;
}

strcat↓

char * strcat ( char * destination, const char * source );

1.将源字符串的副本追加到目标字符串。
2.目标中的终止空字符被源的第一个字符覆盖,并且在目标中由两者串联形成的新字符串的末尾包含一个空字符。
3.目的地和来源不得重叠。
在这里插入图片描述

/* strcat example */
#include <stdio.h>
#include <string.h>

int main()
{
	char str[80];
	strcpy(str, "These ");
	strcat(str, "Strings ");
	strcat(str, "Are ");
	strcat(str, "Concatenated.");
	puts(str);
	return 0;
}

在这里插入图片描述
在这里插入图片描述
output:
在这里插入图片描述

strcmp↓

int strcmp ( const char * str1, const char * str2 );
  • 标准规定:
    第一个字符串大于第二个字符串,则返回大于0的数字
    第一个字符串等于第二个字符串,则返回0
    第一个字符串小于第二个字符串,则返回小于0的数字
    在这里插入图片描述
/* strcmp example */
#include <stdio.h>
#include <string.h>

int main()
{
	char str1[] = "abcd";
	char str2[] = "ab";
	char str3[] = "abedf";
	char str4[] = "abcdr";

	printf("%d\n", strcmp(str1, str2));
	printf("%d\n", strcmp(str1, str3));
	printf("%d\n", strcmp(str1, str4));

	return 0;
}

在这里插入图片描述
在这里插入图片描述

strncpy↓

char * strncpy ( char * destination, const char * source, size_t num );
  • 拷贝num个字符从源字符串到目标空间。
  • 如果源字符串的长度小于num,则拷贝完源字符串之后,在目标的后边追加0,直到num个。
    strncpy
/* strncpy example */
#include <stdio.h>
#include <string.h>

int main()
{
	char str1[] = "To Be Or Not To Be**\0**";
	char str2[30] = { 0 };
	char str3[30] = { 0 };
	char str4[50] = { 0 };

	/* copy to sized buffer (overflow safe): */
	strncpy(str2, str1, sizeof(str2));

	/* partial copy (only 5 chars): */
	strncpy(str3, str2, 5);
	str3[5] = '\0';   /* null character manually added */

	strncpy(str4, str1, 30);

	puts(str1);
	puts(str2);
	puts(str3);
	puts(str4);

	return 0;
}

output:
在这里插入图片描述

strncat↓

char * strncat ( char * destination, const char * source, size_t num );
/* strncat example */
#include <stdio.h>
#include <string.h>

int main()
{
	char str1[20];
	char str2[20];
	strcpy(str1, "To Be ");
	strcpy(str2, "Or Not To Be");
	strncat(str1, str2, 6);
	puts(str1);
	return 0;
}

在这里插入图片描述

strncmp↓

int strncmp ( const char * str1, const char * str2, size_t num );

strncmp

strstr↓

在这里插入图片描述
点击查看strstr函数
⇱在str1中寻找是否含有str2,最后返回值指向 str2 中指定的整个字符序列在 str1 中首次出现的指针,如果序列在 str1 中不存在,则为 null 指针。

/* strstr example */
#include <stdio.h>
#include <string.h>

int main()
{
    char str[] = "This Is A Simple String";
    char* pch;
    pch = strstr(str, "Simple");
    if (pch != NULL)
        strncpy(pch, "Sample", 6);
    puts(str);
    return 0;
}

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

strtok↓

char * strtok ( char * str, const char * delimiters );

delimiters→分隔符

  • delimiters参数是个字符串,定义了用作分隔符的字符集合
  • 第一个参数指定一个字符串,它包含了0个或者多个由delimiters字符串中一个或者多个分隔符分割的标记。
  • strtok函数找到str中的下一个标记,并将其用 \0 结尾,返回一个指向这个标记的指针。(注:strtok函数会改变被操作的字符串,所以在使用strtok函数切分的字符串一般都是临时拷贝的内容
    并且可修改。)
  • strtok函数的第一个参数不为 NULL ,函数将找到str中第一个标记strtok函数将保存它在字符串中的位置。
  • strtok函数的第一个参数为 NULL ,函数将在同一个字符串中被保存的位置开始,查找下一个标记。如果字符串中不存在更多的标记,则返回 NULL 指针。
/* strtok example */
#include <string.h>
#include<stdio.h>
int main()
{
	char arr[] = "Alison@137.com";
	char buf[200] = { 0 };//"Alison@137.com"
	strcpy(buf, arr);
	const char* p = "@.";
	char* str = NULL;
	for (str = strtok(buf, p); str != NULL; str = strtok(NULL, p))
	{
		printf("%s\n", str);
	}
	return 0;

}

在这里插入图片描述
在这里插入图片描述
output:
在这里插入图片描述

strerror↓

char * strerror ( int errnum );

点击查看strerror函数
在这里插入图片描述
在这里插入图片描述

memcpy↓

void * memcpy ( void * destination, const void * source, size_t num );

在这里插入图片描述
在这里插入图片描述

/* memcpy example */
#include <stdio.h>
#include <string.h>
struct {
	char name[40];
	int age;
} person, person_copy;
int main()
{
	char myname[] = "Pierre de Fermat";
	/* using memcpy to copy string: */
	memcpy(person.name, myname, strlen(myname) + 1);
	person.age = 46;
	/* using memcpy to copy structure: */
	memcpy(&person_copy, &person, sizeof(person));
	printf("person_copy: %s, %d \n", person_copy.name, person_copy.age);
	return 0;
}

在这里插入图片描述

memmove↓

void * memmove ( void * destination, const void * source, size_t num );
  • 和memcpy的差别就是memmove函数处理的源内存块和目标内存块是可以重叠的。
  • 如果源空间和目标空间出现重叠,就得使用memmove函数处理。
/* memmove example */
#include <stdio.h>
#include <string.h>
int main ()
{
  char str[] = "memmove can be very useful......";
  memmove (str+20,str+15,11);
  puts (str);
  return 0;
}

memcmp↓

int memcmp ( const void * ptr1, 
             const void * ptr2, 
             size_t num );
  • 比较从ptr1和ptr2指针开始的num个字节
    在这里插入图片描述
/* memcmp example */
#include <stdio.h>
#include <string.h>
int main()
{
	char buffer1[] = "DWgaOtP12df0";
	char buffer2[] = "DWGAOTP12DF0";
	int n;
	n = memcmp(buffer1, buffer2, sizeof(buffer1));
	if (n > 0) 
		printf("'%s' is greater than '%s'.\n", buffer1, buffer2);
	else if (n < 0) 
		printf("'%s' is less than '%s'.\n", buffer1, buffer2);
	else 
		printf("'%s' is the same as '%s'.\n", buffer1, buffer2);
	return 0;
}

在这里插入图片描述

库函数模拟实现

⇲模拟实现strlen

#include <stdio.h>
int my_strlen(const char* str)
{
	int count = 0;
	while (*str++ != '\0')
	{
		count++;
	}//依此往后数,数到'\0'停下,最后返回一个整型数字
	return count;
}
int main()
{
	char arr[] = "abcdef";
	char arr2[] = "abdkdsfjkdsjfl";
	printf("%d\n", my_strlen(arr));
	printf("%d\n", my_strlen(arr2));

	return 0;
}

⇲模拟实现strcpy

#include<stdio.h>
#include<assert.h>
char* my_strcpy(char* des, const char* source)
{
	assert(des && source);//防止传参传过来空指针
	char* start = des;
	while (*des++ = *source++)
	//先把源字符串中的内容依次赋值到目标空间,再++往后
	{
		;
	}
	return start;//最终返回目标空间的起始位置
}

int main()
{
	char arr1[] = "********";
	char arr2[] = "hello";
	printf("%s", my_strcpy(arr1, arr2));
	return 0;
}

⇲模拟实现strcat

#include <stdio.h>
#include <assert.h>

char* my_strcat(char* des,const char* source)
{
	assert(des && source);
	char* ret = des;
	while (*des++)
	//找到目标空间字符串中'\0'的位置
	{
		;
	}
	des--;
	//最后一次循环*des==0后被++所以这里需要在--回到'\0'的位置
	while (*des++ = *source++)
	//依此赋值
	{
		;
	}
	return ret;//最终返回目标空间的起始位置
}

int main()
{
	char arr1[20] = "hello ";
	char arr2[] = "alison";
	my_strcat(arr1, arr2);
	printf("%s", arr1);
	return 0;
}

⇲模拟实现strstr

(暴力求解)
在这里插入图片描述

#include<stdio.h>
#include<assert.h>
char* my_strstr(const char* overall, const char* part)
{
	assert(overall && part);//防止传过来空指针
	char* s1 = overall;
	char* s2 = part;
	char* p = s1;
	while ((*s1 != '\0') && (*s1 != *s2))
	{
		s1++;
	}
	p = s1;
	while (*s1)
	{
		while (*s1++ == *s2++)
		{
			if (*s2 == '\0')
			{
				return p;
			}
		}
		p++;
		s1 = p;
		s2 = part;
	}
	if (*s1 == '\0')
		return NULL;

}
int main()
{
	char arr1[] = "abcdefg";
	char arr2[] = "bcd";
	char arr3[] = "add";
	if (my_strstr(arr1, arr2) == NULL)
	{
		printf("在%s中没找到%s\n", arr1, arr2);
	}
	else
	{
		printf("在%s中找到了%s\n", arr1, arr2);
	}
	if (my_strstr(arr1, arr3) == NULL)
	{
		printf("在%s中没找到%s\n", arr1, arr3);
	}
	else
	{
		printf("在%s中找到了%s\n", arr1, arr3);
	}
	return 0;
}

⇲模拟实现strcmp

#include<stdio.h>
#include<assert.h>
int my_strcmp(const char* e1, const char* e2)
{
	assert(e1 && e2);
	while (*e1++ == *e2++)
	{
		if (*e1 == '\0')
			return 0;
	}
	return *e1 - *e2;
}

int main()
{
	char arr1[] = "abc";
	char arr2[] = "abdc";
	char arr3[] = "abc";
	printf("%d\n", my_strcmp(arr1, arr2));
	printf("%d\n", my_strcmp(arr1, arr3));
	return 0;
}

⇲模拟实现memmove

#include<stdio.h>
#include<assert.h>

void* my_memmove(void* des, const void* src, size_t num)
{
	assert(des && src);
	void* ret = des;
	if (des < src)
	{
		while (num--)
		{
			*((char*)des) = *((char*)src);
			des = (char*)des + 1;
			src = (char*)src + 1;
		}
	}
	else
	{
		while (num--)
		{
			*((char*)des + num) = *((char*)src + num);
		}
	}
	return ret;
}

int main()
{
	char str[] = "Memmove Can Be Very Useful......";
	my_memmove(str + 20, str + 15, 11);
	puts(str);
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

畋坪

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

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

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

打赏作者

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

抵扣说明:

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

余额充值