C 为什么我得到;初始化';字符*';使用类型为';常量字符*';丢弃限定符?

C 为什么我得到;初始化';字符*';使用类型为';常量字符*';丢弃限定符?,c,C,我不明白为什么我自己从clang得到这个警告: function_prototype_const_modifier.c:13:8: warning: initializing 'char *' with an expression of type 'const char *' discards qualifiers [-Wincompatible-pointer-types] char *ptr1 = source; ^

我不明白为什么我自己从
clang
得到这个警告:

function_prototype_const_modifier.c:13:8: warning: initializing 'char *' with an
      expression of type 'const char *' discards qualifiers
      [-Wincompatible-pointer-types]
        char *ptr1 = source;
              ^      ~~~~~~
1 warning generated.
代码非常简单

#include<stdio.h>

char *my_strcpy(char *destination, const char *source);

int main(void) {
    char str1[] = "this is something";  
    char str2[] = "123456789123456789";
    my_strcpy(str2, str1);
    puts(str2);
    return 0;
}
char *my_strcpy(char *destination, const char *source) {
    char *ptr1 = source;
    char *ptr2 = destination;
    while(*ptr1 != '\0') {
        *ptr2++ = *ptr1++;
    }
    *ptr2 = '\0';
    return destination;
}
#包括
char*my_strcpy(char*destination,const char*source);
内部主(空){
char str1[]=“这是一件大事”;
char str2[]=“123456789123456789”;
my_strcpy(str2,str1);
看跌期权(str2);
返回0;
}
char*my_strcpy(char*destination,const char*source){
char*ptr1=源;
char*ptr2=目的地;
而(*ptr1!='\0'){
*ptr2++=*ptr1++;
}
*ptr2='\0';
返回目的地;
}

有什么想法吗?

因为L.H.S的类型是
char*
,而R.H.S的类型是
const char*

原因正是错误所说的:

函数\u prototype\u const\u modifier.c:13:8:警告:使用“const char*”类型的表达式初始化“char*”将丢弃限定符


该语句允许您丢弃
常量
限定符,并允许通过
ptr1
ptr2
修改指向的字符串,因此编译器会抱怨。

您正在将字符常量指针指定给字符指针。
这样做有可能修改字符

您指向内存中的同一区域,但没有将其限定为
常量(参数为)


然后,您允许函数体修改标记为
const
source
的内存部分,它是一个
const char*
,一个指向常量字符的指针,因此不能通过取消引用指针来更改字符(即
source[0]='a';
违反了约束)

但是,将其分配给
char*
会丢弃此约束;一个简单的
char*
表明
ptr1
指针指向的字符不是常量,您现在可以自由写入
ptr1[0]='a'而不获取编译器错误(“诊断消息”)

请考虑传入字符串文字时这意味着什么。由于字符串文字是“只读”(它是
常量字符[]
),因此试图修改其内容是未定义的行为。所以如果你打电话

my_strcpy(destination, "Constant String");
但在代码中,由于某种原因,您编写

ptr1[0] = 'A';

您将不会收到编译器诊断消息,因为
ptr1
是指向非常量字符的指针,但您的程序仍将调用未定义的行为(实际上,很可能会崩溃,因为字符串文本放置在只读内存区域中)。

您只需更改:

char *ptr1 = source;
致:


在这种情况下,我们可以做什么

感谢@user529758的清晰信息

再加上一个答案

修改:

#include<stdio.h>

char *my_strcpy(char *destination, const char *source);

int main(void) {
    char str1[] = "this is something";  
    char str2[] = "123456789123456789";
    my_strcpy(str2, str1);
    puts(str2);
    return 0;
}
char *my_strcpy(char *destination, const char *source) {
    char *ptr1 = (char*)source;
    char *ptr2 = destination;
    while(*ptr1 != '\0') {
        *ptr2++ = *ptr1++;
    }
    *ptr2 = '\0';
    return destination;
}
#包括
char*my_strcpy(char*destination,const char*source);
内部主(空){
char str1[]=“这是一件大事”;
char str2[]=“123456789123456789”;
my_strcpy(str2,str1);
看跌期权(str2);
返回0;
}
char*my_strcpy(char*destination,const char*source){
char*ptr1=(char*)源;
char*ptr2=目的地;
而(*ptr1!='\0'){
*ptr2++=*ptr1++;
}
*ptr2='\0';
返回目的地;
}

我认为
const
意味着指针是常量,而不是指针对象。我可能弄错了。简从右到左读了它(不管怎样,它帮助了我)。指向字符常量的指针。char const*是指向字符的指针常量。@JanDvorak
const
关键字应用于其右侧的术语,如果其右侧没有术语,则仅将
const
关键字应用于其左侧的术语。@H2CO3同意。它右边的术语是
char*
,一个char指针。
#include<stdio.h>

char *my_strcpy(char *destination, const char *source);

int main(void) {
    char str1[] = "this is something";  
    char str2[] = "123456789123456789";
    my_strcpy(str2, str1);
    puts(str2);
    return 0;
}
char *my_strcpy(char *destination, const char *source) {
    char *ptr1 = (char*)source;
    char *ptr2 = destination;
    while(*ptr1 != '\0') {
        *ptr2++ = *ptr1++;
    }
    *ptr2 = '\0';
    return destination;
}