return怎么返回字符串_数据结构的实践心得(字符串管理:mystring)

be5dfa671d55da486f1cbf0417ddd2f8.png

头文件(mystring.h):

#pragma once

#include "seqList.h"

#define StringERROR -99999999

#define StringNumberLENGTH 20

// 取得字符串长度

int mystrlen(char *s);

// 进行内存初始化

char* mymemset(char *p, char val, size_t size);

// 对字符串进行拷贝

char* mystrcpy(char *s, char *outStr);

// 对字符串转换大写

char* myToUpper(char *s, char *outStr);

// 对字符串转换小写

char* myToLower(char *s, char *outStr);

// 取得字符的索引位置

int indexOf(char *s, char c);

// 取得字符串的索引位置

int indexOfStr(char *s, char *subStr);

// 字符串比较

int myEqual(char *s1, char *s2);

// 字符串比较(s1>s2返回1,s1

int mystrcmp(char *s1, char *s2);

// 字符串连接

char* mystrcat(char **s1Out, char *s2);

// 删除字符串

char* mystrdel(char *sOut, char *delStr);

// 替换字符串

char* myReplace(char *sOut, char oldC, char newC);

// 替换字符串(待替换的字符串长度必须相等)

char* myReplaceStr(char *sOut, char *oldStr, char *newStr);

// 字符串逆序输出

char* myReverse(char *s, char *outStr);

// 分割字符串(必须在外部释放顺序表seqList)

seqList mySplit(char *s, char c, char **strList);

// 字符串转换整型

int myatoi(char *s);

// 字符串转换浮点型

double myatof(char *s);

// 整型转换为字符串

char* myitoa(int num, char *outStr);

// 整型转换为字符串

char* myftoa(double num, char *outStr);

程序文件(mystring.c):

#include

#include "mystring.h"

// 取得字符串长度

int mystrlen(char *s)

{

if (!s) return -1;

int i = 0;

// 遍历字符数组,一直到结束符为止

while (s[i])

{

i++;

}

return i;

}

// 进行内存初始化

char* mymemset(char *p, char val, size_t size)

{

if (!p) return p;

int i;

// 循环初始化内存

for (i = 0; i < size; i++)

{

p[i] = val;

}

return p;

}

// 对字符串进行拷贝

char* mystrcpy(char *s, char *outStr)

{

if ((!s) || (!outStr)) return outStr;

int i = 0;

// 遍历字符数组,一直到结束符为止

while (s[i])

{

outStr[i] = s[i]; i++;

}

// 补充结束符

outStr[i] = 0;

return outStr;

}

// 对字符串转换大写

char* myToUpper(char *s, char *outStr)

{

if ((!s) || (!outStr)) return outStr;

int i = 0;

// 遍历字符数组,一直到结束符为止

while (s[i])

{

if ((s[i] >= 97) && (s[i] <= 122))

{

outStr[i] = s[i] - 32;

}

else

{

outStr[i] = s[i];

}

i++;

}

// 补充结束符

outStr[i] = 0;

return outStr;

}

// 对字符串转换小写

char* myToLower(char *s, char *outStr)

{

if ((!s) || (!outStr)) return outStr;

int i = 0;

// 遍历字符数组,一直到结束符为止

while (s[i])

{

if ((s[i] >= 65) && (s[i] <= 90))

{

outStr[i] = s[i] + 32;

}

else

{

outStr[i] = s[i];

}

i++;

}

// 补充结束符

outStr[i] = 0;

return outStr;

}

// 取得字符的索引位置

int indexOf(char *s, char c)

{

if (!s) return -1;

int i = 0;

// 遍历字符数组,一直到结束符为止

while (s[i])

{

if (s[i] == c) break;

i++;

}

return i;

}

// 取得KMP算法的next数组

int* getNext(char *subStr, int subLen, int *outNext)

{

if ((!subLen) ||(!outNext)) return outNext;

// 长度是否有效

if (subLen <= 0) return outNext;

int j = 0, k = -1;

outNext[0] = -1;

while (j < subLen - 1)

{

if ((k == -1) || (subStr[j] == subStr[k]))

{

j++; k++;

// 记录前后缀相等的数量

outNext[j] = k;

}

else

{

k = outNext[k];

}

}

return outNext;

}

// 取得字符串的索引位置

int indexOfStr(char *s, char *subStr)

{

if ((!s) || (!subStr)) return -1;

// 取得待查找的字符串长度

int subLen = mystrlen(subStr);

// 如果长度为空,则退出

if (subLen <= 0) return -1;

// 取得字符串长度

int len = mystrlen(s);

// 如果长度小于待查找的字符串长度,则退出

if (len < subLen) return -1;

// 初始化KMP算法内存

int *next = (int *)malloc(sizeof(int) * subLen);

// 取得KMP算法的next数组

next = getNext(subStr, subLen, next);

int i = 0, j = 0, k;

int index = -1;

int findLen = len - subLen;

// 根据next数组中的值在主串中查找模式

while (i <= findLen)

{

k = i;

// 逐个比较字符

while (s[i] == subStr[j])

{

i++; j++;

// 比较到结束符,则跳出

if (!subStr[j]) break;

}

if (j == subLen)

{

index = k; break;

}

else if (next[j] == -1)

{

i++; j = 0;

}

else

{

j = next[j];

}

}

// 释放KMP算法内存

free(next);

return index;

}

// 字符串比较

int myEqual(char *s1, char *s2)

{

if ((!s1) || (!s2)) return 0;

int i = 0;

// 遍历字符数组,一直到结束符为止

while (s1[i])

{

// 一个字符不相等,则判定字符串不相等

if (s1[i] != s2[i]) return 0;

i++;

}

// 最后比较结束符

return (s1[i] == s2[i]);

}

// 字符串比较(s1>s2返回1,s1

int mystrcmp(char *s1, char *s2)

{

if ((!s1) || (!s2)) return -2;

int i = 0;

// 遍历字符数组,一直到结束符为止

while (s2[i])

{

if (s1[i] > s2[i])

{

return 1;

}

else if (s1[i] < s2[i])

{

return -1;

}

i++;

}

// 最后比较结束符

return (s1[i] > s2[i]);

}

// 字符串连接

char* mystrcat(char **s1Out, char *s2)

{

if ((!*s1Out) || (!s2)) return *s1Out;

// 首先取得字符串长度

int len1 = mystrlen(*s1Out), len2 = mystrlen(s2);

// 如果长度为空,则退出

if ((len1 + len2) <= 0) return *s1Out;

// 重新分配内存地址

*s1Out = (char *)realloc(*s1Out, len1 + len2 + 1);

if (!*s1Out) return *s1Out;

int i;

// 循环字符串s2(包括结束符)

for (i = 0; i <= len2; i++)

{

(*s1Out)[i + len1] = s2[i];

}

return *s1Out;

}

// 删除字符串

char* mystrdel(char *sOut, char *delStr)

{

if ((!*sOut) || (!delStr)) return *sOut;

// 取得待删除的字符串长度

int delLen = mystrlen(delStr);

// 如果长度为空,则退出

if (delLen <= 0) return sOut;

// 取得字符串长度

int len = mystrlen(sOut);

// 如果长度小于待删除的字符串长度,则退出

if (len < delLen) return sOut;

// 初始化KMP算法内存

int *next = (int *)malloc(sizeof(int) * delLen);

// 取得KMP算法的next数组

next = getNext(delStr, delLen, next);

int i = 0, j = 0, k, m;

int findLen = len - delLen, tmpLen;

// 根据next数组中的值在主串中查找模式

while (i <= findLen)

{

k = i;

// 逐个比较字符

while (sOut[i] == delStr[j])

{

i++; j++;

// 比较到结束符,则跳出

if (!delStr[j]) break;

}

if (j == delLen)

{

tmpLen = len - k - delLen;

// 循环移动后续的字符内容(包括结束符)

for (m = 0; m <= tmpLen; m++)

{

sOut[k + m] = sOut[k + m + delLen];

}

// 重新比较移动后的字符,重新从第一个字符开始比较

i -= delLen; j = 0;

}

else if (next[j] == -1)

{

i++; j = 0;

}

else

{

j = next[j];

}

}

// 释放KMP算法内存

free(next);

return sOut;

}

// 替换字符串

char* myReplace(char *sOut, char oldC, char newC)

{

if (!sOut) return sOut;

int i = 0;

// 遍历字符数组,一直到结束符为止

while (sOut[i])

{

// 如果等于旧字符,则替换为新字符

if (sOut[i] == oldC) sOut[i] = newC;

i++;

}

return sOut;

}

// 替换字符串(待替换的字符串长度必须相等)

char* myReplaceStr(char *sOut, char *oldStr, char *newStr)

{

if ((!sOut) || (!oldStr) || (!newStr)) return sOut;

// 取得待替换的字符串长度

int oldLen = mystrlen(oldStr), newLen = mystrlen(newStr);

// 如果长度为空,或者替换的字符串长度不相等,则退出

if ((oldLen <= 0) || (oldLen != newLen)) return sOut;

// 取得字符串长度

int len = mystrlen(sOut);

// 如果长度小于待替换的字符串长度,则退出

if (len < oldLen) return sOut;

// 初始化KMP算法内存

int *next = (int *)malloc(sizeof(int) * oldLen);

// 取得KMP算法的next数组

next = getNext(oldStr, oldLen, next);

int i = 0, j = 0, k, m;

int findLen = len - oldLen;

// 根据next数组中的值在主串中查找模式

while (i <= findLen)

{

k = i;

// 逐个比较字符

while (sOut[i] == oldStr[j])

{

i++; j++;

// 比较到结束符,则跳出

if (!oldStr[j]) break;

}

if (j == oldLen)

{

// 循环替换新的字符内容

for (m = 0; m < newLen; m++)

{

sOut[k + m] = newStr[m];

}

// 重新从第一个字符开始比较

j = 0;

}

else if (next[j] == -1)

{

i++; j = 0;

}

else

{

j = next[j];

}

}

// 释放KMP算法内存

free(next);

return sOut;

}

// 字符串逆序输出

char* myReverse(char *s, char *outStr)

{

if ((!s) || (!outStr)) return outStr;

// 首先取得字符串长度

int len = mystrlen(s);

int i;

// 循环字符串的字符内容

for (i = 0; i < len; i++)

{

outStr[i] = s[len - i - 1];

}

// 补充结束符

outStr[i] = 0;

return outStr;

}

// 分割字符串(必须在外部释放顺序表seqList)

seqList mySplit(char *s, char c, char *strList)

{

seqList seq;

// 初始化顺序表(Null)

initializeSeqListNull(&seq);

if ((!s) || (!strList)) return seq;

int len = 0, num = 0;

// 遍历字符数组,一直到结束符为止

while (s[len])

{

// 计算有多少个待分割的字符

if (s[len] == c)

{

strList[len] = 0;

num++;

}

else

{

strList[len] = s[len];

}

len++;

}

// 补充结束符

strList[len] = 0;

// 没有待分割字符则退出

if (num <= 0) return seq;

// 初始化顺序表

initializeSeqList(&seq, num + 1);

// 记录第一个字符串指针地址

insertSeqList(&seq, seq.len, (seqElemType)strList);

int i;

// 循环字符串

for (i = 0; i < len; i++)

{

if (!strList[i])

{

// 记录每个字符串指针地址

insertSeqList(&seq, seq.len, (seqElemType)(strList + i + 1));

}

}

// 返回字符串指针数组(顺序表seqList)

return seq;

}

// 字符串转换为整型

int myatoi(char *s)

{

if ((!s)) return StringERROR;

// 首先取得字符串长度

int len = mystrlen(s);

int numRe = 0;

// 十位的进位

int dec = 1;

// 是否为负数

int minus = 0;

int i;

// 倒序循环字符串

for (i = len - 1; i >= 0; i--)

{

if ((s[i] >= 48) && (s[i] <= 57))

{

// 字符串转数值

numRe += ((s[i] - 48) * dec);

// 十位的进位

dec *= 10;

}

else if (s[i] == '-')

{

minus++;

}

}

// 判断是否为负数(出现了单数个负号)

if ((minus % 2) > 0) numRe = -numRe;

return numRe;

}

// 字符串转换为浮点型

double myatof(char *s)

{

if ((!s)) return StringERROR;

// 取得字符串长度

int len = mystrlen(s);

// 取得小数点的索引位置

int index = indexOf(s, '.');

double numRe = 0;

// 十分位的进位

double frac = 0.1;

// 是否为负数

int minus = 0;

int i;

// 从index开始循环字符串(小数部分)

for (i = index + 1; i < len; i++)

{

if ((s[i] >= 48) && (s[i] <= 57))

{

// 字符串转数值

numRe += ((s[i] - 48) * frac);

// 十分位的进位

frac *= 0.1;

}

else if (s[i] == '-')

{

minus++;

}

}

// 十位的进位

int dec = 1;

// 倒序循环字符串(整数部分)

for (i = index - 1; i >= 0; i--)

{

if ((s[i] >= 48) && (s[i] <= 57))

{

// 字符串转数值

numRe += ((s[i] - 48) * dec);

// 十位的进位

dec *= 10;

}

else if (s[i] == '-')

{

minus++;

}

}

// 判断是否为负数(出现了单数个负号)

if ((minus % 2) > 0) numRe = -numRe;

return numRe;

}

// 整型转换为字符串

char* myitoa(int num, char *outStr)

{

if ((!outStr)) return outStr;

char tmp[StringNumberLENGTH] = { 0 };

// 被除数

int div = num;

// 先转换为绝对值

if (div < 0) div = -div;

// 索引

int i = 0;

// 余数

int mod;

while (div > 0)

{

// 按位计算余数

mod = div % 10;

// 记录余数(数值转字符串)

tmp[i] = mod + 48;

// 按位计算被除数

div /= 10;

i++;

}

// 负数补充负号“-”

if (num < 0)

{

tmp[i] = '-'; i++;

}

// 对字符串逆序输出

return myReverse(tmp, outStr);

}

// 整型转换为字符串

char* myftoa(double num, char *outStr)

{

if ((!outStr)) return outStr;

char tmp[StringNumberLENGTH] = { 0 };

// 被除数

double div = num;

// 先转换为绝对值

if (div < 0) div = -div;

// 整数部分

int divInt = div;

// 小数部分

double divDec = div - divInt;

// 索引

int i = 0;

// 余数

int mod;

// 整数部分

while (divInt > 0)

{

// 按位计算余数

mod = divInt % 10;

// 记录余数(数值转字符串)

tmp[i] = mod + 48;

// 按位计算整数部分

divInt /= 10;

i++;

}

// 负数补充负号“-”

if (num < 0)

{

tmp[i] = '-'; i++;

}

// 对整数部分逆序输出

outStr = myReverse(tmp, outStr);

// 如果有小数则补充小数点“.”

if (divDec > 0)

{

outStr[i] = '.'; i++;

int count = 0;

// 小数部分

do 

{

// 按位计算小数部分

divDec *= 10;

// 按位取整

mod = divDec;

// 记录小数(数值转字符串)

outStr[i] = mod + 48;

// 重算小数

divDec -= mod;

// 小数最多只转换六位(避免浮点数小数一直不为零)

i++; count++;

}

while ((divDec > 0) && (count < 6));

// 补充结束符

outStr[i] = 0;

}

return outStr;

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值