1. 程式人生 > >【經典】C語言字串函式原型

【經典】C語言字串函式原型

strlen / strcmp / strcat / strcpy / memset / strstr / atoi / itoa /

/** 程式碼演示 -strlen.c **/
size_t mystrlen2 (char *s) // 核心
{
 char *p = s;
 while (*p)
  p++;
 return p - s;
}

/** 程式碼演示 -strcmp.c **/
int mystrcmp (char *s1, char *s2)
{
 char *p = s1;
 while (*p) {
  if (*p > *s2)
   return 1;
  if (*p < *s2)
   return -1;
  p++;
  s2++;
 }
 return *s2 == 0 ? 0 : -1;
}

/** 程式碼演示 -strcat.c **/


char *mystrcat (char *s1, char *s2)
{
 char *p = s1;
 while (*s1)
  s1++;
 while (*s1++ = *s2++);
 return p; // 首地址
}

/** 程式碼演示 -strcpy.c **/
char *mystrcpy (char *dest, char *src)
{
 char *p = dest;
 while (*dest++ = *src++);
 return p;
}

/** 程式碼演示 -memset.c **/ 
void *mymemset (void *s, char c, size_t len)
{
 char *p = s;
 while (len--)
  *p++ = c;
 return s;
}

/** 程式碼演示 - strstr.c **/

const char *mystrstr (const char *s, const char *sub_s)
{
    int i, j;
    int tmp = 0;
    for (i = 0; s[i] != '\0'; i++) { // i遍歷主串,包含子串即返回i下標位置
        j = 0; // 子串位置每次從頭開始
        while (s[tmp++] == sub_s[j++]) { // tmp遍歷主串,主做判斷下標0到字串末尾\0
            if (sub_s[j] == '\0')
                return &s[i];
        }  
    }  
    return NULL;
}


/** 程式碼演示 - itoa.c **/

void itoa (char* buf, unsigned int num) {
    unsigned int tmp = 0;
    buf[0] = '0';
    buf[1] = 'x';
    int i = 9; 
    while (num) {
        tmp = num % 16;
        if (tmp > 9)
            buf[i] = 'a' + tmp - 10;
        else
            buf[i] = '0' + tmp;
        num /= 16;
        i--;
    }
    while (i >= 2) {
        buf[i--] = '0'; // 0x0000005a 中間補全的0
    }
    buf[10] = 0; // 最後1位的\0
}

/* itoa.c 版本2 - 原理一樣 */
#include <stdio.h>
#define ARR_SIZE 20
void myitoa (char *dest, int num)
{
    int i = 0, j = 0;
    while (num) {
        dest[i++] = num % 10 + '0';
        num /= 10;
    }  
    dest[i] = '\0';
    for (j = i; j >= 0; j--)
        printf ("%c", dest[j]);
    printf ("\n");
}

int main ()
{
    int num = 0;
    char str[ARR_SIZE] = {0};
    printf ("輸入一個數字:");
    scanf ("%d", &num);
    myitoa (str, num);
    printf ("轉換為字串:%s\n", str);
    return 0;
}

/** 程式碼演示 - atoi.c **/
int atoi (char* s) { 
    int num = 0;
    char* tmp = s;
    while (*tmp++) {
        if (*tmp >= '0' && *tmp <= '9')
            num = num * 10 + (*tmp - '0'); // '0' <==> 48
        else
            break;
    }  
    return num;
}


/** 程式碼演示 - atoi.c  - 版本2  **/
int myAtoi(const char * str)
{
    int num = 0; //儲存轉換後的數值
int isNegative = 0; //記錄字串中是否有負號
int n =0;
char *p = str;
if(p == NULL) //
判斷指標的合法性
{
    return -1;
}
while(*p++ != '\0') //
計算數字符串度
{
    n++;
}
p = str;
if(p[0] == '-') //
判斷陣列是否有負號
{
    isNegative = 1;
}
char temp = '0';
for(int i = 0 ; i < n; i++)
{
  char temp = *p++;
   if(temp > '9' ||temp < '0') //濾除非數字字元
    {
        continue;
    }
    if(num !=0 || temp != '0') //濾除字串開始的0 字元
    {
        temp -= 0x30; //將數字字元轉換為數值
        num += temp *int( pow(10 , n - 1 -i) );
    }
}
if(isNegative) //
如果字串中有負號,將數值取反
{
    return (0 - num);
}
else
{
    return num; //返回轉換後的數值
}
}
注意:此段程式碼只是實現了十進位制字串到數字的轉化,讀者可以自己去實現2進位制,8進位制,10進位制,16進位制的轉化。


/** 字串倒序:倒序一個字串程式碼演示 **/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main (void)
{
    char *src = "hello";
    char *dest = NULL;
    int len = strlen (src);
    dest = (char *)malloc (len+1);
    char *d = dest;
    char *s = &src[len-1];
    while (len-- != 0) 
        *d++ = *s--;
    *d = '\0';
    printf ("dest = %s\n", dest);
    free (dest);
    dest = NULL;
    return 0;
}


判斷是否是迴文函式:
bool fun(char *p)
{
    int len = strlen(p);
    char *q = p + len - 1; 
    while (p < q) { // 當兩個指標指向的是同一個陣列則可以比較大小 
        if ((*p++) != (*q--))
        return flase;
    }
    return true;
}