如果您将其保存在main 中,因为您的sentences 内存是静态的(无法删除),您可以这样做:
#include <string.h>
#include <stdio.h>
int main()
{
char sentences[] = "The first sentence.The second sentence.The third sentence";
char* sentence[3];
unsigned int i;
sentence[0] = strtok(sentences, ".");
for (i=1;i<sizeof(sentence)/sizeof(sentence[0]);i++)
{
sentence[i] = strtok(NULL, ".");
}
for (i=0;i<sizeof(sentence)/sizeof(sentence[0]);i++)
{
printf("%d: %s\n",i,sentence[i]);
}
return 0;
}
在一般情况下,您首先必须复制您的输入字符串:
char *sentences_dup = strdup(sentences);
sentence[0] = strtok(sentences_dup, ".");
原因有很多:
- 你不知道输入的生命周期/范围,它通常是一个指针/一个参数,所以一旦输入内存被释放/超出范围,你的句子就可能无效
- 传递的缓冲区可能是
const:你不能修改它的内存(strtok修改传递的缓冲区)
- 在上面的示例中将
sentences[] 更改为*sentences,并且您指向的是只读区域:您必须复制缓冲区。
不要忘记存储重复的指针,因为您可能需要在某个时候释放它。
另一种选择是在那里复制:
for (i=1;i<sizeof(sentence)/sizeof(sentence[0]);i++)
{
sentence[i] = strdup(strtok(NULL, "."));
}
这样您就可以立即释放大的标记化字符串,并且句子有自己独立的记忆。
编辑:这里剩下的问题是你仍然需要提前知道你的输入中有多少个句子。
为此,您可以计算点数,然后分配适当数量的指针。
int j,nb_dots=0;
char pathsep = '.';
int nb_sentences;
int len = strlen(sentences);
char** sentence;
// first count how many dots we have
for (j=0;j<len;j++)
{
if (sentences[j]==pathsep)
{
nb_dots++;
}
}
nb_sentences = nb_dots+1; // one more!!
// allocate the array of strings
sentence=malloc((nb_sentences) * sizeof(*sentence));
现在我们有了字符串的数量,我们可以执行strtok 循环。请注意使用nb_sentences 而不是sizeof(sentence)/sizeof(sentence[0]),因为数组类型的变化现在已经无关紧要(价值1)。
但此时你也可以完全摆脱strtok,就像另一个answer of mine中建议的那样