栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > C/C++/C#

C语言-字符函数和字符串函数

C/C++/C# 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

C语言-字符函数和字符串函数

本文介绍处理字符和字符串的库函数的使用和注意事项
C语言中对字符和字符串的处理很是频繁,但是C语言本身是没有字符串类型的,字符串通常放在常量字符串中或者字符数组中。
字符串常量适用于那些对它不做修改的字符串函数.

文章目录
  • 一、求字符串长度strlen
  • 二、长度不受限制的字符串函数
    • 1.strcpy
    • 2.strcat
    • 3.strcmp
  • 三、长度受限制的字符串函数介绍
    • 1.strncpy
    • 2.strncat
    • 3. strncmp
  • 四、字符串查找
    • 1.strstr
    • 2.strtok
  • 五、错误信息报告
    • strerror
  • 六、字符操作
    • 1.字符分类函数:
    • 2.字符转换:
  • 七、内存操作函数
    • 1.memcpy
    • 2.memmove
    • 3.memset
    • 4.memcmp

一、求字符串长度strlen


需要注意的点:
1.字符串已经 ‘’ 作为结束标志,strlen函数返回的是在字符串中 ‘’ 前面出现的字符个数(不包含 ‘’ )。
2.参数指向的字符串必须要以 ‘’ 结束。
3.注意函数的返回值为size_t,是无符号的( 易错 )
看下面代码:

#include 
int main()
{
    if (strlen("abc")-strlen("abcdef"))
		{
			printf("1");
		}
		else
		{
			printf("2");
		}
		return 0;
}

打印结果为:1
因为if中的两个strlen返回结果都为size_t类型,相减也是无符号
4.strlen函数的模拟实现:

#include
int my_strlen(const char*str)  //const修饰只读变量,防止变量被改
{ 
     int count = 0;                      
     while (*str++)//当*str =''跳出循环,注意*str++ 操作符++优先级高于*操作符 
     {                   
       count++;    
     }
     return count;
}
int main()
{
     char*p = "abcde";//遇到''停止计数
     printf("%d",my_strlen(p));
     return 0;
}
二、长度不受限制的字符串函数 1.strcpy

字符串拷贝

源字符串必须以 ‘’ 结束。会将源字符串中的 ‘’ 拷贝到目标空间。
目标空间必须足够大,以确保能存放源字符串。目标空间必须可变。
模拟实现:
三种方式:
方式1:

//计数器方式
int my_strlen(const char * str)
{
    int count = 0;
    while(*str)
    {
        count++;
        str++;
    }
    return count; 
}

方式2:

//不能创建临时变量计数器
int my_strlen(const char * str)
{
    if(*str == '')
    return 0;
    else
    return 1+my_strlen(str+1);
}

方式3:

//指针-指针的方式
int my_strlen(char *s) 
{
       char *p = s;
       while(*p != ‘0’ )
              p++;
       return p-s; 
}
2.strcat

字符串连接,字符串追加
源字符串必须以 ‘’ 结束。
目标空间必须有足够的大,能容纳下源字符串的内容。
目标空间必须可修改。
模拟实现:

//strcat返回的是起始空间的地址
char* my_strcat(char* dest, const char* src)
{
	assert(dest && src);

	char* ret = dest;
	//找到目标字符串的末尾
	while (*dest)
	{
		dest++;
	}
	//追加源字符串直到
	while (*dest++ = *src++)
	{
		;
	}

	return 0;
}
3.strcmp

是比较字符串的内容,不是长度
标准规定:
第一个字符串大于第二个字符串,则返回大于0的数字
第一个字符串等于第二个字符串,则返回0
第一个字符串小于第二个字符串,则返回小于0的数字
模拟实现:

int my_strlen(const char* s1, const char* s2)
{
	assert(s1 && s2);

	while (*s1 == *s2)
	{
		if (*s1 == *s2)
			return 0;
		s1++;
		s2++;
	}

	return *s1 - *s2;
}
三、长度受限制的字符串函数介绍 1.strncpy

1.拷贝num个字符从源字符串到目标空间。
2.如果源字符串的长度小于num,则拷贝完源字符串之后,在目标的后边追加0,直到num个。
3.模拟实现:

//1.参数顺序
//2.函数的功能,停止条件
//3.assert
//4.const修饰指针
//5.函数返回值
//6.题目出自《高质量C/C++编程》书籍最后的试题部分
char *my_strcpy(char *dest, const char*src)
{ 
     char *ret = dest;
     assert(dest != NULL);
     assert(src != NULL);
 
     while((*dest++ = *src++))
     {
         ;
     }
     return ret; 
 }
2.strncat

模拟实现:

char *my_strcat(char *dest, const char*src)
{
    char *ret = dest;
    assert(dest != NULL);
    assert(src != NULL);
    while(*dest)
    {
        dest++;
    }
    while((*dest++ = *src++))
    {
        ;
    }
    return ret; 
}
#include 
#include 
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;
}
3. strncmp

比较到出现另个字符不一样或者一个字符串结束或者num个字符全部比较完。

模拟实现:

int my_strcmp (const char * src, const char * dst)
{
        int ret = 0 ;
        assert(src != NULL);
        assert(dest != NULL);
        while( ! (ret = *(unsigned char *)src - *(unsigned char *)dst) && *dst)
                ++src, ++dst;
        if ( ret < 0 )
                ret = -1 ;
        else if ( ret > 0 )
                ret = 1 ;
        return( ret );
}

四、字符串查找 1.strstr

在一个字符串中查找子字符串
模拟实现:

char* strstr(const char* str1, const char* str2)
{
	char* cp = (char*)str1;
	char* s1, * s2;
	if (!*str2)
		return((char*)str1);
	while (*cp)
	{
		s1 = cp;
		s2 = (char*)str2;
		while (*s1 && *s2 && !(*s1 - *s2))
			s1++, s2++;
		if (!*s2)
			return(cp);
		cp++;
	}
	return(NULL);
}
2.strtok

1.sep参数是个字符串,定义了用作分隔符的字符集合
2.第一个参数指定一个字符串,它包含了0个或者多个由sep字符串中一个或者多个分隔符分割的标记。
3.strtok函数找到str中的下一个标记,并将其用 结尾,返回一个指向这个标记的指针。(注:strtok函数会改变被操作的字符串,所以在使用strtok函数切分的字符串一般都是临时拷贝的内容并且可修改。)
4.strtok函数的第一个参数不为 NULL ,函数将找到str中第一个标记,strtok函数将保存它在字符串中的位置。
5.strtok函数的第一个参数为 NULL ,函数将在同一个字符串中被保存的位置开始,查找下一个标记。
6.如果字符串中不存在更多的标记,则返回 NULL 指针。

#include 
int main()
{
   char *p = "ymz@abcd.efg";
   const char* sep = ".@";
   char arr[30];
   char *str = NULL;
   strcpy(arr, p);//将数据拷贝一份,处理arr数组的内容
   for(str=strtok(arr, sep); str != NULL; str=strtok(NULL, sep))
   {
   printf("%sn", str);
   }
}
五、错误信息报告 strerror


返回错误码所对应的错误信息

#include 
#include 
#include //必须包含的头文件
int main ()
{
  FILE * pFile;
  pFile = fopen ("unexist.ent","r");
  if (pFile == NULL)
    printf ("Error opening file unexist.ent: %sn",strerror(errno));
    //errno: Last error number
  return 0; }
Edit & Run
六、字符操作 1.字符分类函数:

函数 如果他的参数符合下列条件就返回真
iscntrl 任何控制字符
isspace 空白字符:空格‘ ’,换页‘f’,换行’n’,回车‘r’,制表符’t’或者垂直制表符’v’
isdigit 十进制数字 0~9
isxdigit 十六进制数字,包括所有十进制数字,小写字母af,大写字母AF
islower 小写字母a~z
isupper 大写字母A~Z
isalpha 字母az或AZ
isalnum 字母或者数字,az,AZ,0~9
ispunct 标点符号,任何不属于数字或者字母的图形字符(可打印)
isgraph 任何图形字符
isprint 任何可打印字符,包括图形字符和空白字符

2.字符转换:
int tolower ( int c );
int toupper ( int c );
#include 
#include 
int main ()
{
    int i=0;
    char str[]="Test String.n";
    char c;
    while (str[i])
{
    c=str[i];
    if (isupper(c)) 
        c=tolower(c);
    putchar (c);
    i++;
    }
    return 0; 
}
七、内存操作函数 1.memcpy

1.和memcpy的差别就是memmove函数处理的源内存块和目标内存块是可以重叠的。
2.如果源空间和目标空间出现重叠,就得使用memmove函数处理。
3.模拟实现:

void * memcpy ( void * dst, const void * src, size_t count) 
{
        void * ret = dst;
        assert(dst);
        assert(src);
        
        while (count--) 
        {
                *(char *)dst = *(char *)src;
                dst = (char *)dst + 1;
                src = (char *)src + 1;
       }
        return(ret);
}
2.memmove

void * memmove ( void * dst, const void * src, size_t count) 
{
        void * ret = dst;
        if (dst <= src || (char *)dst >= ((char *)src + count)) 
        {
                
                while (count--) 
                {
                        *(char *)dst = *(char *)src;
                        dst = (char *)dst + 1;
                        src = (char *)src + 1;
                }
        }
        else 
        {
                
                dst = (char *)dst + count - 1;
                src = (char *)src + count - 1;
                while (count--) 
                {
                        *(char *)dst = *(char *)src;
                        dst = (char *)dst - 1;
                        src = (char *)src - 1;
                }
       } 
       return(ret);
}

3.memset

4.memcmp

比较从ptr1和ptr2指针开始的num个字节

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/330068.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号