首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> C >> 關於C

C語言實現動態字串庫:String.h 完整源碼解析

     編輯:關於C

C 標準庫字串操作功能有限且易出錯。本文提供一個完整的動態字串庫實現,支援建立、拷貝、連接、比較、查找、分割、子串搜尋等操作,採用鏈表式緩衝區管理,適合嵌入式或無標準庫環境。

核心資料結構

typedef char* String;
typedef int Status;

#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0

// 安全檢查巨集
#define CHECK(t) do { if(!(t)) return 0; } while(0)

// 靜態緩衝區(用於 StrTok)
static String STRBUFFER = 0;

核心函數實現

1. 基礎操作

// 字串長度
int StrLen(String buf) {
    String temp = buf;
    while(*temp++);
    return temp - buf - 1;
}

// 分配字串空間(含結束符)
String StrMake(int length) {
    return (String)malloc(length + 1);
}

// 字串查找字符
String StrChr(String buf, char ch, int length) {
    while(length-- && *buf++ != ch);
    return buf - 1;
}

2. 字串修改操作

// 字串連接(動態擴容)
void StrCat(String *dest, String src) {
    String temp = (String)malloc(StrLen(*dest) + StrLen(src) + 1);
    String head = temp;
    String d = *dest;
    
    while(*d) *temp++ = *d++;
    while(*src) *temp++ = *src++;
    *temp = '\0';
    *dest = head;
}

// 字串拷貝
void StrCpy(String *dest, String src) {
    *dest = StrMake(StrLen(src));
    String temp = *dest;
    while(*src) *temp++ = *src++;
    *temp = 0;
}

// 釋放字串
void StrFree(String *str) {
    free(*str);
    *str = 0;
}

3. 比較與輸出

// 字串比較(類 strcmp)
int StrCmp(String buf1, String buf2) {
    do {
        if(*buf1 > *buf2) return 1;
        if(*buf1 < *buf2) return -1;
        if(!*buf1) break;
        buf1++; buf2++;
    } while(1);
    return 0;
}

// 列印字串
Status StrPrint(String str) {
    CHECK(str);
    puts(str);
    return TRUE;
}

4. 進階操作:分割與搜尋

// 字串分割(類 strtok,可重入)
String StrTok(String dest, String src) {
    if(dest) StrCpy(&STRBUFFER, dest);
    CHECK(src && STRBUFFER && *STRBUFFER);
    
    int length = StrLen(src);
    String ch = StrChr(src, *STRBUFFER, length);
    
    // 跳過分隔符
    if(*ch == *STRBUFFER) {
        do {
            *STRBUFFER++ = '\0';
            CHECK(*STRBUFFER);
            ch = StrChr(src, *STRBUFFER, length);
        } while(*ch == *STRBUFFER);
    }
    
    String result = STRBUFFER;
    String temp = result;
    
    // 尋找下一個分隔符
    while(*temp) {
        ch = StrChr(src, *temp, length);
        if(*ch == *temp) {
            *temp++ = '\0';
            CHECK(*temp);
            break;
        } else temp++;
    }
    STRBUFFER = temp;
    return result && *result ? result : 0;
}

// 子串搜尋(類 strstr)
String StrStr(String dest, String src) {
    CHECK(dest && src && *dest && *src);
    do {
        String temp = src, rt = dest;
        while(*temp == *rt) { temp++; rt++; }
        if(!*temp) return dest;
        CHECK(*rt);
        dest++;
    } while(*dest);
    return 0;
}

使用範例

int main() {
    String s1 = StrMake(20);
    String s2 = StrMake(20);
    
    StrCpy(&s1, "Hello");
    StrCpy(&s2, " World");
    StrCat(&s1, s2);           // "Hello World"
    
    StrPrint(s1);
    
    String token = StrTok("a,b,c", ",");
    while(token) {
        StrPrint(token);       // 輸出 a, b, c
        token = StrTok(0, ",");
    }
    
    StrFree(&s1);
    StrFree(&s2);
    return 0;
}

設計亮點與不足

優點缺點/風險
完全動態分配,無固定緩衝區限制StrTok 使用靜態變數,非執行緒安全
介面簡潔,語義接近標準庫缺乏錯誤碼細分,僅回傳 0/1
StrTok 支援多字符分隔符頻繁 malloc/free 可能產生碎片
無標準庫依賴,適合裸機環境未處理 UTF-8 多位元組字符

改進建議

  • 引入引用計數或 COW(Copy-On-Write)減少拷貝
  • 改用結構體封裝 len、capacity、data 避免重複計算長度
  • 提供 StrDup、StrCmpIgnoreCase 等常用擴展
  • StrTok 改為傳入上下文結構體實現可重入
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved