/*************************************************
函数名: strdup
功 能: 将串拷贝到新建的位置处
用 法: char *strdup(char *str);
这个函数在linux的man手册里解释为:
The strdup() function returns a pointer toa new string which is a
duplicate of the string s. Memory for the new string is obtained with
malloc(), and can be freed with free().The strndup() function is similar,
but onlycopies at most n characters. If s is longer than n,
only n characters are copied, and a terminating NUL is added.
Allocates enough storage via malloc() for a copy of the string, copies the
string into the new memory, and returns a pointer to it.
头文件: <stdlib.h>
strdup()主要是拷贝字符串s的一个副本,由函数返回值返回,
这个副本有自己的内存空间,和s不相干。strdup函数复制一个字符串,
使用完后要记得删除在函数中动态申请的内存,strdup函数的参数不能为NULL,
一旦为NULL,就会报段错误,因为该函数包括了strlen函数,而该函数参数不能是NULL
复制字符串,返回指向被复制字符串的指针。所需空间由malloc()分配,
且可以由free()释放。需要注意的是,在调用完这个函数后,一定要记得释放内存空间。
**************************************************/
char * my_strdup(const char *str)
{
char *p;
if (!str)
return(NULL);
if (p = malloc(my_strlen(str) + 1))
return(my_strcpy(p,str));
return(NULL);
}
char * __strdup (const char *s)
{
size_t len =strlen (s) + 1;
void *new =malloc (len);
if (new == NULL)
return NULL;
return (char *)memcpy (new, s, len);
}
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
unsigned int Test()
{
charbuf[]="Hello,World!";
char* pb =strndup(buf,strlen(buf));
return (unsignedint)(pb);
}
int main()
{
unsigned int pch= Test();
printf("Testing:%s\n",(char*)pch);
free((void*)pch);
return 0;
}
在Test函数里使用strndup而出了Test函数仍可以操作这段内存,并且可以释放
strdup的危险之处就在于申请的是堆内存,并且把malloc封装在函数内部,
必须时刻谨记着内存释放,严防内存泄露,可以显式的使用malloc实现strdup功能
char *dest = malloc( strlen( src ) + 1 );
assert( dest != NULL );
strcpy( dest, src );
/**********************************************
atoi 将字符串转化为数字
头文件:stdlib.h
**********************************************/
isspace(int x)
{
if(x==' '||x=='\t'||x=='\n'||x=='\f'||x=='\b'||x=='\r')
return 1;
else
return 0;
}
isdigit(int x)
{
if(x<='9'&&x>='0')
return 1;
else
return 0;
}
int atoi(const char *nptr)
{
int c; /* current char */
int total; /* current total */
int sign; /* if '-', then negative, otherwise positive */
/* skip whitespace */
while ( isspace((int)(unsigned char)*nptr) )
++nptr;
c = (int)(unsigned char)*nptr++;
sign = c; /* save sign indication */
if (c == '-' || c == '+')
c = (int)(unsigned char)*nptr++; /* skip sign */
total = 0;
while (isdigit(c))
{
total = 10 * total + (c - '0'); /* accumulate digit */
c = (int)(unsigned char)*nptr++; /* get next char */
}
if (sign == '-')
return -total;
else
return total; /* return result, negated if necessary */
}
/*********************************************************************
itoa()函数的原型为: char *itoa( int value, char *string,int radix);
itoa()函数有3个参数: 第一个参数是要转换的数字,
第二个参数是要写入转换结果的目标字符串,
第三个参数是转换数字时所用的基数。
itoa并不是一个标准的C函数,它是Windows特有的,如果要写跨平台的程序,请用sprintf。
是Windows平台下扩展的,标准库中有sprintf,功能比这个更强,用法跟printf类似:
char str[255];
sprintf(str, "%x", 100); //将100转为16进制表示的字符串。
*********************************************************************/
void rever(char s[])
{
int len=strlen(s);
int i=0;
int j=len-1;
char c;
while (i<j)
{
c=s[i];
s[i]=s[j];
s[j]=c;
i++;
j--;
}
}
void my_itoa(int n, char s[])
{
int i=0;
int sign=0;
//判断符号
if((sign=n)<0)
n=-n;
//分解生成逆序字符串
do
{
s[i++]=n%10+'0';
} while ((n/=10)>0);
if(sign<0)
s[i++]='-';
//结尾注意添加\0
s[i]='\0';
rever(s);
}
char *itoa(int num, char *str, int radix)
{
char string[] = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
char* ptr = str;
int i;
int j;
while (num)
{
*ptr++ = string[num % radix];
num /= radix;
if (num < radix)
{
*ptr++ = string[num];
*ptr = '\0';
break;
}
}
j = ptr - str - 1;
for (i = 0; i < (ptr - str) / 2; i++)
{
int temp = str[i];
str[i] = str[j];
str[j--] = temp;
}
return str;
}
/**********************************************************************************
函数名: strtok
功 能: 查找由在第二个串中指定的分界符分隔开的单词
用 法: char *strtok(char *str1, char *str2);
原型:char *strtok(char *s, const char *delim);
分解字符串为一组字符串。s为要分解的字符串,delim为分隔符字符串。
strtok()用来将字符串分割成一个个片段。参数s指向欲分割的字符串,
参数delim则为分割字符串,当strtok()在参数s的字符串中发现到参数delim的
分割字符时则会将该字符改为\0 字符。在第一次调用时,strtok()
必需给予参数s字符串,往后的调用则将参数s设置成NULL。
每次调用成功则返回被分割出片段的指针。
返回值 从s开头开始的一个个被分割的串。当没有被分割的串时则返回NULL。
所有delim中包含的字符都会被滤掉,并将被滤掉的地方设为一处分割的节点。
strtok函数在C和C++语言中的使用 strtok函数会破坏被分解字符串的完整,
调用前和调用后的s已经不一样了。如果要保持原字符串的完整,
可以使用strchr和sscanf的组合等。
**************************************************************************************/
#include <string.h>
#include <stdio.h>
int main(void)
{
char input[16] = "abc,d";
char *p;
/**/ /* strtok places a NULL terminator
in front of the token, if found */
p = strtok(input, ",");
if (p) printf("%s\n", p);
/**/ /* A second call to strtok using a NULL
as the first parameter returns a pointer
to the character following the token */
p = strtok(NULL, ",");
if (p) printf("%s\n", p);
return 0;
}
#include <stdio.h>
#include <string.h>
int main ()
{
char str[] ="- This, a sample string.";
char * pch;
printf ("Splitting string \"%s\" into tokens:\n",str);
pch = strtok (str," ,.-");
while (pch != NULL)
{
printf ("%s\n",pch);
pch = strtok (NULL, " ,.-");
}
return 0;
}
Output:
Splitting string "- This, a sample string." into tokens:
This
a
sample
string
#include <iostream>
#include <cstring>
using namespace std;
int main()
{
char sentence[]="This is a sentence with 7 tokens";
cout<<"The string to be tokenized is:\n"<<sentence<<"\n\nThe tokens are:\n\n";
char *tokenPtr=strtok(sentence," ");
while(tokenPtr!=NULL)
{
cout<<tokenPtr<<'\n';
tokenPtr=strtok(NULL," ");
}
cout<<"After strtok, sentence = "<<sentence<<endl;
return 0;
}