标准函数库
数组
拷贝数据
void *memcpy(void *dest, const void *src, size_t count); // => wmemcpy
memcpy
从src
拷贝count
字节数据到dest
;wmemcpy
则拷贝count
个宽字符的数据。如果源和目的区域有重叠,则该函数的行为未定义。
注意:应该保证目的缓存应该大于或等于源缓存。
void *memmove(void *dest,const void *src, size_t count);
// => wmemmove、memmove_s、wmemmove_s
从src
到dest
拷贝count
字节(memmove
)或字符(wmemmove
)。如果源和目的区域有重叠,则该函数能保证覆盖区域的数据被覆盖之前被正确拷贝。
注意:应该保证目的缓存应该大于或等于源缓存。
设置数据
memset
比较
memcmp
C字符串
char
型字符串==存储变长字符编码==(Linux平台为UTF-8
,Windows平台为GBK
),以单字节“null
”结尾;wchar_t
存储定长字符编码(UTF-16
),以两个“null
”结尾。
wchar_t
字符串的处理函数以wcs
开头,对应char
字符串以str
开头的函数。
char str[5] = {'T', 'h', 'i', 's', 0}; // string as array
当使用字符串字面值初始化时,对应的字符串是不能修改的,因此将其声明为常量。
const char str[] = "this is a string";
const char* ptr = "this is a string";
属性
size_t strlen(const char *s); // => wcslen
计算字符串长度,遇到'\0
'结束,==长度以字节计数==;如果是中文,则一般一个中文字符占3字节。
拼接
char *strcat(char *dest, const char *src);
char *strncat(char *dest, const char *src, size_t n);
将字符串src
连接到dest
的尾部。从dest
的\0
开始。strncat
与strcat
的区别在:strncat
最多使用src
的n
个字节;如果src
的长度大于或等于n
,则strncat
的src
字符串不需要是null
结尾。
strlen()
和strcat()
是两个比较耗时的操作。在程序中应该少使用。
比较
int strcmp(const *s1,const *s2);
int strncmp(const char *s1, const char *s2, size_t n);
int strcasecmp(const char *s1, const char *s2);
int strncasecmp(const char *s1, const char *s2, size_t n);
比较s1
和s2
。strncmp
只比较最多n
个字符。strcasecmp
忽略大小写。
s1 = s2
的时候返回值 =0;s1 < s2
的时候返回至 <0;s1 > s2
的时候返回值 >0;
查找
char *strchr(const char *s, char c);
char *strrchr(const char *s, int c);
char *strchrnul(const char *s, int c);
strchr
返回s
中首次出现c
的位置的指针,strrchr
返回最后出现c
的位置的指针。如果s
中不存在c
则返回NULL
。
strchrnul
与strchr
类似,只是在找不到c
的时候,返回字符串的null
位置指针,而不是NULL
。
char *strstr(const char *haystack, const char *needle);
char *strcasestr(const char *haystack, const char *needle);
返回haystack
中needle
字符串首次出现的位置的指针(不比较结束符null
)。若果没找到则返回NULL
。strcasestr
在查找时忽略字符串的大小写。
复制
char *strcpy(char *dest, const char *src); // => wcscpy,wcscpy_s
char *strncpy(char *dest, const char *src, size_t n); // => wcscat,wcscat_s
拷贝src
指向的字符串到dest
指向的缓冲区。strncpy
则最多拷贝n
个字符,如果前n
个字符没有以null
结束,则目标字符串也不会以null
结束。
类型转换
#include <cstdlib>
int atoi(const char *nptr);
long atol(const char *nptr);
long long atoll(const char *nptr);
将字符串转换成int
,long
和long long
型整数。atoi()
会扫描参数nptr
字符串,跳过前面的空格,直到遇上数字或者正负号才开始装换,而再遇到非数字或者字符串结束时停止转换。atoi
不会检测错误。
double atof(const char *nptr);
将字符串转换为浮点数。atof
不会检测错误。
long int strtol(const char *nptr, char **endptr, int base);
long long int strtoll(const char *nptr, char **endptr, int base);
strtol
根据base
的值就将nptr
指向的字符串转换为整数。base
的取值范围为2~36
,或为0
。 字符串可以在开头包含任意数量的空格,空格之后可以包含“+
”或“-
”。如果base = 0
,若字符串包含前缀“0x
”,字符串字符串将按照16进制解析;若字符串包含前缀“0”,字符串字符串将按照8进制解析;其他情况则按10进制解析。解析停止于首个非法字符。
如果endptr
不是NULL
,则strtol
将把首个非法字符的地址存储在*endptr
中。如果nptr
中没有数字,则*endptr=nptr
并返回0,如果nptr!=NULL
且*endnptr=NULL
,则全部是合法字符。
strtoll
与strtol
类似,只是返回值的类型为long long int
。如果发生下溢出,则strtol
返回LONG_MIN
;如果发生上溢出,则strtol
返回LONG_MAX
。两种情况下,errno
被设置为ERANGE
。strtoll
也是类似,只是返回值为LLONG_MIN
和LLONG_MAX
。
unsigned long int strtoul(const char *nptr, char **endptr, int base);
unsigned long long int strtoull(const char *nptr, char **endptr, int base);
strtoul
根据base
的值将nptr
指向的字符串转换为无符号整数,转换规则与strtol
类似。
double strtod(const char *nptr, char **endptr);
float strtof(const char *nptr, char **endptr);
long double strtold(const char *nptr, char **endptr);
将nptr
指向的字符串转换为浮点数。
格式化
int sprintf(char *buf, char *format,arg_list);
int snprintf(char *restrict buf, size_t n, const char *restrict format,...);
sprintf()
是一个功能强大的函数。跟printf(char *format,arg_list)
的功能类似。不过,printf()
是将格式化的字符输出到屏幕,而sprintf()
则是将格式化的字符放入到buf
中。这个函数对操作缓冲区buf
,并对其内容加以格式带来了极大的方便。
snprintf()
最多从源串format
中拷贝n-1
个字符到目标串buf
中,然后再在后面加一个'\0'
.如果目标串的大小为n
的话,将不会溢出。snprintf()
如果成功则返回存入数组的字符数,若错误则返回负值。
int sscanf(string str, string fmt, mixed var1, mixed var2 ... );
int scanf(const char *format [,argument]... );
从一个字符串中读进与指定格式相符的数据。sscanf
与scanf
类似,都是用于输入的,只是后者以屏幕(stdin
)为输入源,前者以固定字符串为输入源。其中,format
可以是一个或多个
{%[*][width][{h|l|I64|L}]type|' '|'\t'|'\n'|非%符号}
格式化输入
char buf[512];
sscanf("123456 ", "%s", buf);
sscanf("123456 ", "%4s", buf); // 取最大长度为4字节的字符串
正则匹配:sscanf
的%[]
类似于一个正则表达式,但却没有正则表达式强大,所以如果对于比较复杂的字符串处理,建议使用正则表达式。
sscanf("123456 abcdedf", "%[^ ]", buf); // 取遇到空格为止字符串
sscanf("123456abcdedfBCDEF", "%[1-9a-z]", buf); //仅包含指定字符集的字符串
sscanf("123456abcdedfBCDEF", "%[^A-Z]", buf);
给定一个字符串iios/12DDWDFF@122
,获取 /
和 @
之间的字符串,先将 "iios/
"过滤掉,再将非'@'
的一串内容送到buf
中
sscanf("iios/12DDWDFF@122", "%*[^/]/%[^@]", buf);
sscanf(“hello, world”, "%*s%s", buf);
%*s
表示第一个匹配到的%s
被过滤掉,即'hello'
被过滤了;如果没有空格则结果为NULL。
其他方法
strace strcspn strings strdup strip strpbrk
strdupa strtok strtouq strerror strtok_r strverscmp
strerror_r strsep strxfrm strchrnul strfmon strsignal
strfry strspn strcoll strndup string strndupa
时间
时间格式化
size_t strftime(
char *strDest,
size_t maxsize,
const char *format,
const struct tm *timeptr
);
format
用于声明格式化字符串。
时间字符串解析
strptime
系统调用
文件系统
#include <stdio.h>
int rename( const char *oldfname, const char *newfname ); // 更改文件名
系统接口
system
解释执行一条命令。函数将命令传递给命令环境(Shell),如果输入命令为空,则system
函数检查命令环境是否存在。在使用system
函数前,必须显式调用刷新流(调用fflush
或_flushall
)或者关闭流。
#include <stdlib.h>
int system(const char *command );
int _wsystem(const wchar_t *command);
_wsystem
是宽字符版本的system
函数。_tsystem
则根据程序中是否定义了_UNICODE
来确定使用的函数。如果输入命令为空,而命令解释器为找到,则返回0并且将
errno
设为``ENOENT,否则返回一个非零值;如果输入命令不为空,而命令解释器可以找到,则函数返回值就是命令解释器返回的值。如果返回-1,表明发生了错误,
errno`设置为以下值:
E2BIG
ENOENT
未能找到解释器ENOEXEC
解释器的格式无效,不能执行ENOMEM
内存不足。