error: result of comparison against a string literal is unspecified for C
error: result of comparison against a string literal is unspecified for C
所以我想和 C 开个小玩笑,但我不知道我做错了什么。我看到错误“error: result of comparison against a string literal is unspecified”并且不知道如何解决它,有人可以帮忙吗。
#include<stdio.h>
#include<cs50.h>
int main(void){
string a = get_string("ENTER YOUR NAME FOR READING\n");
if (a == "david")
;
{
printf("...");
}
}
您不能使用比较运算符比较 c 中的两个字符串。
尝试使用
strcmp(const char* one, const char* two)
也就是你的情况
使用
#include<stdio.h>
#include<cs50.h>
int main(void){
char[] a = get_string("ENTER YOUR NAME FOR READING\n");
char[] b = "david";
if (!strcmp(a,"david"))
{
printf("...");
}
}
此外,c 中的字符串未声明为字符串。它们被声明为 char 数组
编译器接受像这样比较两个字符指针 char *a, *b; a == b;
,但是如果您使用这样的语法来比较字符串值,那么您可能得不到预期的结果。有时它可能计算为 true
或有时计算为 false
。原因是,程序会检查 a
和 b
是否指向相同的地址,而不是检查它们是否具有相同的字符串值。考虑下面的程序。
#include <stdio.h>
int main()
{
char* a = "test";
char* b;
if ((b="test") == a)
printf("Impossible\n");
else
printf("Thought so\n");
printf("%p %p\n", a, b);
return 0;
}
输出
Impossible
0x55b6bd52d004 0x55b6bd52d004
正如您从输出中看到的那样,if
块的计算结果为 true
。原因也在输出中; a
和 b
指向相似的地址。为什么?
It comes from the string-pooling, one of the compiler optimization. Even though a
and b
are initialized at different points in the program, as they are referring to the same string constant, the string constant is initialized only once by the compiler.
这是可执行文件的objdump
。
$ objdump -s -j .rodata
a.out: file format elf64-x86-64
Contents of section .rodata:
2000 01000200 74657374 00496d70 6f737369 ....test.Impossi
2010 626c6500 54686f75 67687420 736f0025 ble.Thought so.%
2020 70202570 0a00 p %p..
test
只初始化一次。为了快速检查,请考虑该程序的输出及其 objdump
.
#include <stdio.h>
int main()
{
char* a = "test";
char* b;
if ((b="test1") == a)
printf("Impossible\n");
else
printf("Thought so\n");
printf("%p %p\n", a, b);
return 0;
}
输出
Thought so
0x557a96aa9004 0x557a96aa9009
objdump
$ objdump -s -j .rodata a.out
a.out: file format elf64-x86-64
Contents of section .rodata:
2000 01000200 74657374 00746573 74310049 ....test.test1.I
2010 6d706f73 7369626c 65005468 6f756768 mpossible.Though
2020 7420736f 00257020 25700a00 t so.%p %p..
从输出中可以明显看出,a
和 b
指向不同的位置,并且它们都具有不同的字符串值,这些值由编译器分别初始化。那么,如果 a
和 b
具有相似的字符串值,那么 a==b
是否总是计算为真?考虑下面的程序。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main()
{
char* a = malloc(sizeof(char) * 5);
strcpy(a, "test");
char* b;
if ((b="test") == a)
printf("Impossible\n");
else
printf("Thought so\n");
printf("%p %p\n", a, b);
return 0;
}
输出
Thought so
0x5607d9938260 0x5607d91fb004
即使 a
和 b
具有相同的字符串值,if
的计算结果为 false
。为什么?地址a
指向的是malloc()
创建的属于可执行文件的堆段,而地址b
指向的属于可执行文件的数据段,它们是确实不一样。
那么我们应该如何比较字符串值呢?
嗯,很简单,已经有库函数可以执行此任务。您可以将它们与 string.h
一起使用。考虑以下代码。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main()
{
char* a = malloc(sizeof(char) * 5);
strcpy(a, "test");
char* b = "test";
char* c;
if (strcmp((c="test"), a) == 0)
printf("Impossible\n");
else
printf("Thought so\n");
if (strcmp(b, a) == 0)
printf("Impossible\n");
else
printf("Thought so\n");
if (strcmp(b, c) == 0)
printf("Impossible\n");
else
printf("Thought so\n");
printf("%p %p %p\n", a, b, c);
return 0;
}
输出
Impossible
Impossible
Impossible
0x556debf41260 0x556deac28004 0x556deac28004
无论 a
、b
和 c
指向何处,如果它们都具有相同的字符串值,则 strcmp()
returns 0
。
您的代码存在三个问题:
1.
if (a == "david")
a
衰减到指向数组 a
.
第一个元素的指针
"david"
是字符串文字。
使用 if
语句,您尝试将数组 a
的地址与字符串文字 "david"
的地址进行比较。字符串比较在 C 中无法正常工作。
使用strcmp()
-headerstring.h
比较字符串。
strcmp()
returns 如果字符串相等则为 0。要使 if
条件变为 true
,您需要使用 !
否定运算符。
2.
if
条件和 if
body 之间错位了 ;
。删除它。
3.
不推荐使用 cs50.h
。如果您不需要明确使用它,请将您的手拿开。
#include <stdio.h>
#include <string.h>
int main (void) {
char a[20];
printf("ENTER YOUR NAME FOR READING:\n");
if (!fgets(a, sizeof a, stdin))
{
fputs("Failure at input", stderr);
// further Error routine.
}
a[strcspn(a, "\n")] = 0;
if (!strcmp(a,"david"))
{
printf("...");
}
}
所以我想和 C 开个小玩笑,但我不知道我做错了什么。我看到错误“error: result of comparison against a string literal is unspecified”并且不知道如何解决它,有人可以帮忙吗。
#include<stdio.h>
#include<cs50.h>
int main(void){
string a = get_string("ENTER YOUR NAME FOR READING\n");
if (a == "david")
;
{
printf("...");
}
}
您不能使用比较运算符比较 c 中的两个字符串。 尝试使用
strcmp(const char* one, const char* two)
也就是你的情况 使用
#include<stdio.h>
#include<cs50.h>
int main(void){
char[] a = get_string("ENTER YOUR NAME FOR READING\n");
char[] b = "david";
if (!strcmp(a,"david"))
{
printf("...");
}
}
此外,c 中的字符串未声明为字符串。它们被声明为 char 数组
编译器接受像这样比较两个字符指针 char *a, *b; a == b;
,但是如果您使用这样的语法来比较字符串值,那么您可能得不到预期的结果。有时它可能计算为 true
或有时计算为 false
。原因是,程序会检查 a
和 b
是否指向相同的地址,而不是检查它们是否具有相同的字符串值。考虑下面的程序。
#include <stdio.h>
int main()
{
char* a = "test";
char* b;
if ((b="test") == a)
printf("Impossible\n");
else
printf("Thought so\n");
printf("%p %p\n", a, b);
return 0;
}
输出
Impossible
0x55b6bd52d004 0x55b6bd52d004
正如您从输出中看到的那样,if
块的计算结果为 true
。原因也在输出中; a
和 b
指向相似的地址。为什么?
It comes from the string-pooling, one of the compiler optimization. Even though
a
andb
are initialized at different points in the program, as they are referring to the same string constant, the string constant is initialized only once by the compiler.
这是可执行文件的objdump
。
$ objdump -s -j .rodata
a.out: file format elf64-x86-64
Contents of section .rodata:
2000 01000200 74657374 00496d70 6f737369 ....test.Impossi
2010 626c6500 54686f75 67687420 736f0025 ble.Thought so.%
2020 70202570 0a00 p %p..
test
只初始化一次。为了快速检查,请考虑该程序的输出及其 objdump
.
#include <stdio.h>
int main()
{
char* a = "test";
char* b;
if ((b="test1") == a)
printf("Impossible\n");
else
printf("Thought so\n");
printf("%p %p\n", a, b);
return 0;
}
输出
Thought so
0x557a96aa9004 0x557a96aa9009
objdump
$ objdump -s -j .rodata a.out
a.out: file format elf64-x86-64
Contents of section .rodata:
2000 01000200 74657374 00746573 74310049 ....test.test1.I
2010 6d706f73 7369626c 65005468 6f756768 mpossible.Though
2020 7420736f 00257020 25700a00 t so.%p %p..
从输出中可以明显看出,a
和 b
指向不同的位置,并且它们都具有不同的字符串值,这些值由编译器分别初始化。那么,如果 a
和 b
具有相似的字符串值,那么 a==b
是否总是计算为真?考虑下面的程序。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main()
{
char* a = malloc(sizeof(char) * 5);
strcpy(a, "test");
char* b;
if ((b="test") == a)
printf("Impossible\n");
else
printf("Thought so\n");
printf("%p %p\n", a, b);
return 0;
}
输出
Thought so
0x5607d9938260 0x5607d91fb004
即使 a
和 b
具有相同的字符串值,if
的计算结果为 false
。为什么?地址a
指向的是malloc()
创建的属于可执行文件的堆段,而地址b
指向的属于可执行文件的数据段,它们是确实不一样。
那么我们应该如何比较字符串值呢?
嗯,很简单,已经有库函数可以执行此任务。您可以将它们与 string.h
一起使用。考虑以下代码。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main()
{
char* a = malloc(sizeof(char) * 5);
strcpy(a, "test");
char* b = "test";
char* c;
if (strcmp((c="test"), a) == 0)
printf("Impossible\n");
else
printf("Thought so\n");
if (strcmp(b, a) == 0)
printf("Impossible\n");
else
printf("Thought so\n");
if (strcmp(b, c) == 0)
printf("Impossible\n");
else
printf("Thought so\n");
printf("%p %p %p\n", a, b, c);
return 0;
}
输出
Impossible
Impossible
Impossible
0x556debf41260 0x556deac28004 0x556deac28004
无论 a
、b
和 c
指向何处,如果它们都具有相同的字符串值,则 strcmp()
returns 0
。
您的代码存在三个问题:
1.
if (a == "david")
a
衰减到指向数组 a
.
"david"
是字符串文字。
使用 if
语句,您尝试将数组 a
的地址与字符串文字 "david"
的地址进行比较。字符串比较在 C 中无法正常工作。
使用strcmp()
-headerstring.h
比较字符串。
strcmp()
returns 如果字符串相等则为 0。要使 if
条件变为 true
,您需要使用 !
否定运算符。
2.
if
条件和 if
body 之间错位了 ;
。删除它。
3.
不推荐使用 cs50.h
。如果您不需要明确使用它,请将您的手拿开。
#include <stdio.h>
#include <string.h>
int main (void) {
char a[20];
printf("ENTER YOUR NAME FOR READING:\n");
if (!fgets(a, sizeof a, stdin))
{
fputs("Failure at input", stderr);
// further Error routine.
}
a[strcspn(a, "\n")] = 0;
if (!strcmp(a,"david"))
{
printf("...");
}
}