字符串函数详解(看这一篇就足够了)(上)

简介: 字符串函数详解(看这一篇就足够了)(上)

本节小编将讲解一下相关字符串函数的使用和模拟,干货满满!!!

重点介绍处理字符和字符串的库函数的使用和注意事项

一.相关函数分类

1.求字符串长度

strlen

2.长度不受限制的字符串函数

strcpy strcat strcmp

3.长度受限制的字符串函数介绍

strncpy  strncat  strncmp

4.字符串查找

strstr  strtok

5.错误信息报告

strerror


前言

C语言中对字符和字符串的处理很是频繁,但是C语言本身是没有字符串类型的,字符串通常放在常量字符串中或者字符数组中。

字符串常量 适用于那些对它不做修改的字符串函数.

二. 函数介绍

2.1 strlen 长度计算

1.字符串已经 '\0' 作为结束标志,strlen函数返回的是在字符串中 '\0' 前面出现的字符个数(不包含 '\0' )。

#include <stdio.h>
 include <string.h>
 int main(){
 char arr[]="abcdef";//abcdef\0
 int len=strlen(arr);
 printf("%d",len);
 return 0;
 }
 结果:6

2.参数指向的字符串必须要以 '\0' 结束。

#include <stdio.h>
 include <string.h>
 int main(){
 char arr[]={'b','i','t'};//
 int len=strlen(arr);
 printf("%d",len);
 return 0;
 }
 运行结果为随机值

3.注意函数的返回值为size_t,是无符号的( 易错 )

//size_t strlen ( const char * str );C
 //size_t 为无符号整型
 #include <stdio.h>
 #include <string.h>
 int main(){
  const char*str1 = "abcdef";
  const char*str2 = "bbb";
  if(strlen(str2)-strlen(str1)>0)
  {
  printf("str2>str1\n");
  } 
  else
  {
  printf("srt1>str2\n");
  }
  return 0;
 }
 运行结果:str2>str1

strlen返回的是无符号整型,两个无符号整型 运算结果还是无符号整型,尽管相减是-3,但是当做无符号整型处理,存到内存的补码将会当成正数。可以直接进行比较或者强制转换类型。

学会strlen函数的模拟实现

计数器

#include <stdio.h>
#include <string.h>
#include <assert.h>
#define N 100
 
 int my_strlen(const char *str)
 {
     int count = 0;
     assert(str);
     while (*str != '\0')
     {
         count++;
         str++;
     }
     return count;
 }
 
 int main()
 {
     char arr[N] = {0};
     printf("输入字符串:\n");
     scanf("%s", arr);
     int n = my_strlen(arr);
     printf("%d\n", n);
     return 0;
 }
 int main(){
   char ch[N];
   //printf("请输入字符串:\n");
   gets(ch);
   printf("%d\n",mystrlen(ch));
   return 0;
 }
 int  mystrlen(const char str[ ])
 {
  int  i ;
  int len = 0;    //计数器置0 
  for (i=0; str[i]!='\0'; i++) {   
   len++; 
  }
   return len;
 }

指针-指针(也可计算长度)

#include <stdio.h>
#define N 100
int my_strlen(char *s)
{
char *p = s;
while (*p != '\0')
p++;
return p - s;
}
 
 int main()
{
char str[N] ={0};
scanf ("%s",str);
int length = my_strlen(str);
printf("字符串长度:%d\n", length);
return 0;
}

补充知识:assert断言

assert是C语言中的一个宏定义,用于在程序中进行断言(assertion)。它的作用是在代码中插入一条断言条件,用于检查某个表达式的结果是否为真。如果断言条件为假,即表达式结果为0,则会触发断言错误。

assert宏的语法如下:

#include

void assert(int expression);

其中,expression是一个要进行断言的条件表达式,通常是一个返回布尔值的表达式。如果expression为假(即0),assert宏会触发断言错误。

断言错误的输出通常包含了触发断言的源文件、行号以及一条错误消息。断言错误通常会导致程序终止执行,以帮助开发者快速发现并定位问题。

assert的主要用途是在开发和调试阶段进行错误处理和调试信息的输出。通过合理地使用断言,我们可以在代码中插入一些逻辑检查点,确保程序在正确的条件下执行,同时帮助发现和修复潜在的问题。

需要注意的是,断言通常在开发过程中使用,在发布版本中会被禁用。这是因为断言仅用于开发和调试,而不应该成为生产代码中的错误处理机制。

示例用法:

#include <stdio.h>
 #include <assert.h>
 
 int main() {
     int x = 10;
     assert(x > 0);  // 断言x大于0
     printf("断言通过\n");
 
     int y = 0;
     assert(y != 0);  // 断言y不等于0
     printf("这行代码不会被执行\n");
 
     return 0;
 }

在上述示例中,第一个断言 assert(x > 0); 是正确的,因此程序会输出 "断言通过"。而第二个断言 assert(y != 0); 是错误的,因为y等于0,所以会触发断言错误,并终止程序的执行。

2.2 strcpy 拷贝

Copies the C string pointed by source into the array pointed by destination, including the

terminating null character (and stopping at that point).

源字符串必须以 '\0' 结束。会将源字符串中的 '\0' 拷贝到目标空间。目标空间必须足够大,以确保能存放源字符串。目标空间必须可变。

学会模拟实现。

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

错误用法

int main(){
const char*p="abcdef";
char arr[]="bit";
strcpy(p,arr);//error 目标区域不可修改,常量字符串
return 0;
}

模拟实现

#include <stdio.h>
#include <string.h>
#include <assert.h>
char* my_strcpy(char* p1, const char* p2) {
    assert(p1);  //如果为空指针,则报错
    assert(p2);
    char* ret = p1;
    while ((*p1++ = *p2++)) {
}
   return ret;
}
int main() {
    char arr1[100] = {0};
    char arr2[100] = {0};  // 修改为合适的大小,以避免缓冲区溢出
    printf("输入字符串:");
    scanf("%s", arr2);
    my_strcpy(arr1, arr2);
    printf("%s\n", arr1);  // 打印复制后的字符串
    return 0;
}

2.3 strcat 字符串追加

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

源字符串必须以 '\0' 结束。目标空间必须有足够的大,能容纳下源字符串的内容。目标空间必须可修改。

字符串自己给自己追加,如何?不能,会破坏原字符串。

模拟实现

#include <stdio.h>
#include <string.h>
#include <assert.h>
char *my_strcat(char *dest, const char*src)
{
    char *ret = dest;
    assert(dest != NULL);
    assert(src != NULL);
//寻找\0
while(*dest)//while(*dest !='\0')
{
dest++;
 }
while((*dest++ = *src++)){
    ;
}
return ret;
}
int main(){
char arr1[]="I love ";
char arr2[100]={0};
scanf("%s",arr2);
  my_strcat(arr1, arr2);
  printf("%s\n", arr1);  // 打印追加后的字符串
  return 0;
}

2.4 strcmp 字符串比较

字符串的字典序比较是指按照字典(词典)的排序方式来比较字符串的大小。在字典序中,字符串按照字符的 ASCII 值的顺序进行比较。

具体来说,对于两个字符串进行字典序比较时,从左到右逐个比较对应位置上的字符的 ASCII 值。如果两个字符相同,则继续向后比较下一个字符,直到遇到不同的字符,或者至少其中一个字符串结束。

int strcmp ( const char * str1, const char * str2 );

标准规定

第一个字符串大于第二个字符串,则返回大于0的数字

第一个字符串等于第二个字符串,则返回0

第一个字符串小于第二个字符串,则返回小于0的数字

那么如何判断两个字符串?

模拟实现

#include <stdio.h>
#include <string.h>
//#include <assert.h>
int my_strcmp(char *str1, char*str2){
    while(*str1==*str2){
        if(*str1=='\0')
        return 0;
        str1++;
        str2++;
    }
    if (*str1>*str2)  //这几行也可以直接替换成  return(*str1-*str2);
      return 1;
    else
      return -1;
}
int main(){
    char str1[100]={0};
    char str2[100]={0};
    printf("请输入字符串\n");
    scanf("%s",str1);
    scanf("%s",str2);
    int ret=my_strcmp(str1,str2);
    if (ret==0)
     printf("=\n");
    else if(ret>0)
     printf(">\n");
     else
     printf("<");
    return 0;
}

以下三个函数第三个参数控制了字符个数

2.5 strncpy

char * strncpy ( char * destination, const char * source, size_t num );

拷贝num个字符从源字符串到目标空间。

如果源字符串的长度小于num,则拷贝完源字符串之后,在目标的后边追加\0,直到num个。

#include <stdio.h>
#include <string.h>
int main(){
  char dest[20] = "Hello";
  char src[] = " World";
  strncat(dest, src, 6);
  printf("%s", dest);  // Output: Hello World
return 0;
}

2.6 strncat

追加num个字符从源字符串到目标空间。

char * strncat ( char * destination, const char * source, size_t num );
#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);
 printf ("%s\n",str1);
 return 0;
 }

运行结果:To be or not

字符串函数详解(看这一篇就足够了)(下):https://developer.aliyun.com/article/1624350

目录
相关文章
|
8月前
|
存储 C语言
C语言中如何选择合适的方式将整数转换为浮点数
C语言中如何选择合适的方式将整数转换为浮点数
1749 0
|
人工智能 搜索推荐 算法
C语言第十一练——输出本机的C语言基本数据类型最大最小取值范围
C语言第十一练——输出本机的C语言基本数据类型最大最小取值范围
77 0
|
C语言
C语言进阶第六课-----------字符分类函数和内存的开辟 1
C语言进阶第六课-----------字符分类函数和内存的开辟
|
存储 编译器 C语言
C语言进阶第六课-----------字符分类函数和内存的开辟 2
C语言进阶第六课-----------字符分类函数和内存的开辟
|
C语言
c语言之计算字节大小的举例
c语言之计算字节大小的举例
121 0
|
3月前
|
C语言
字符串函数详解(看这一篇就足够了)(下)
字符串函数详解(看这一篇就足够了)(下)
67 2
|
3月前
|
C语言
【C语言】三位数(1-4)不重复组合
【C语言】三位数(1-4)不重复组合
|
7月前
|
安全 编译器 C语言
【再识C进阶3(下)】详细地认识字符分类函数,字符转换函数和内存函数
【再识C进阶3(下)】详细地认识字符分类函数,字符转换函数和内存函数
|
8月前
|
存储 编译器 C语言
【C语言】求任意两整数的和入门详解
【C语言】求任意两整数的和入门详解
50 0