我尝试过使用strncmp,但只有在我给它提取一个特定数量的字节时它才有用。
char line[256] = This "is" an example. //I want to extract "is"
char line[256] = This is "also" an example. // I want to extract "also"
char line[256] = This is the final "example". // I want to extract "example"
char substring[256]
我如何提取“”之间的所有元素?并将其放在变量substring?
中答案 0 :(得分:7)
注意:在我意识到编写代码会导致问题后我编辑了这个答案,因为strtok
不喜欢对const char*
变量进行操作。这更像是我编写示例的工件,而不是基本原理的问题 - 但显然它应该是双重downvote。所以我修好了。
以下工作(使用gcc在Mac OS 10.7上测试):
#include <stdio.h>
#include <string.h>
int main(void) {
const char* lineConst = "This \"is\" an example"; // the "input string"
char line[256]; // where we will put a copy of the input
char *subString; // the "result"
strcpy(line, lineConst);
subString = strtok(line,"\""); // find the first double quote
subString=strtok(NULL,"\""); // find the second double quote
printf("the thing in between quotes is '%s'\n", subString);
}
以下是它的工作原理:strtok
查找“分隔符”(第二个参数) - 在本例中是第一个"
。在内部,它知道“它到底有多远”,如果再次使用NULL
作为第一个参数(而不是char*
)再次调用它,它将从那里再次启动。因此,在第二次调用时,它返回“恰好是第一个和第二个双引号之间的字符串”。这就是你想要的。
警告: strtok
通常会使用'\0'
替换分隔符,因为它会“输入”输入。因此,您必须依靠此方法修改输入字符串。如果这是不可接受的,您必须先制作本地副本。本质上,当我将字符串常量复制到变量时,我在上面这样做。通过调用line=malloc(strlen(lineConst)+1);
和free(line);
之后执行此操作会更简洁 - 但如果您打算将其包装在函数内,则必须考虑返回值必须在函数后保持有效返回...因为strtok
返回指向字符串内正确位置的指针,所以它不会复制该令牌。将指针传递到您希望结果结束的空间,并在函数内创建该空间(具有正确的大小),然后将结果复制到其中,这是正确的做法。这一切都非常微妙。如果不清楚,请告诉我!
答案 1 :(得分:0)
这是一个很长的方法:假设要提取的字符串将使用引号 (修正了以下评论中kieth建议的错误检查)
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(){
char input[100];
char extract[100];
int i=0,j=0,k=0,endFlag=0;
printf("Input string: ");
fgets(input,sizeof(input),stdin);
input[strlen(input)-1] = '\0';
for(i=0;i<strlen(input);i++){
if(input[i] == '"'){
j =i+1;
while(input[j]!='"'){
if(input[j] == '\0'){
endFlag++;
break;
}
extract[k] = input[j];
k++;
j++;
}
}
}
extract[k] = '\0';
if(endFlag==1){
printf("1.Your code only had one quotation mark.\n");
printf("2.So the code extracted everything after that quotation mark\n");
printf("3.To make sure buffer overflow doesn't happen in this case:\n");
printf("4.Modify the extract buffer size to be the same as input buffer size\n");
printf("\nextracted string: %s\n",extract);
}else{
printf("Extract = %s\n",extract);
}
return 0;
}
<强>输出(1):强>
$ ./test
Input string: extract "this" from this string
Extract = this
<强>输出(2):强>
$ ./test
Input string: Another example to extract "this gibberish" from this string
Extract = this gibberish
输出(3):( Kieth建议的错误检查)
$ ./test
Input string: are you "happy now Kieth ?
1.Your code only had one quotation mark.
2.So the code extracted everything after that quotation mark
3.To make sure buffer overflow doesn't happen in this case:
4.Modify the extract buffer size to be the same as input buffer size
extracted string: happy now Kieth ?
<强> -------------------------------------------- -------------------------------------------------- ---------------------------------- 强>
虽然没有要求它 - 以下代码从输入字符串中提取多个单词,只要它们在引号中:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(){
char input[100];
char extract[50];
int i=0,j=0,k=0,endFlag=0;
printf("Input string: ");
fgets(input,sizeof(input),stdin);
input[strlen(input)-1] = '\0';
for(i=0;i<strlen(input);i++){
if(input[i] == '"'){
if(endFlag==0){
j =i+1;
while(input[j]!='"'){
extract[k] = input[j];
k++;
j++;
}
endFlag = 1;
}else{
endFlag =0;
}
//break;
}
}
extract[k] = '\0';
printf("Extract = %s\n",extract);
return 0;
}
<强>输出:强>
$ ./test
Input string: extract "multiple" words "from" this "string"
Extract = multiplefromstring
答案 2 :(得分:0)
您是否尝试过查看strchr
功能?您应该能够调用该函数两次以获取指向"
字符的第一个和第二个实例的指针,并使用memcpy
和指针算法的组合来获得您想要的内容。
答案 3 :(得分:0)
如果你想在没有库支持的情况下这样做......
void extract_between_quotes(char* s, char* dest)
{
int in_quotes = 0;
*dest = 0;
while(*s != 0)
{
if(in_quotes)
{
if(*s == '"') return;
dest[0]=*s;
dest[1]=0;
dest++;
}
else if(*s == '"') in_quotes=1;
s++;
}
}
然后调用它
extract_between_quotes(line, substring);
答案 4 :(得分:0)
#include <string.h>
...
substring[0] = '\0';
const char *start = strchr(line, '"') + 1;
strncat(substring, start, strcspn(start, "\""));
省略了边界和错误检查。避免strtok
,因为它有副作用。