#include<stdio.h>
void foo1(const char**p)
{ }
void foo2(const char*p)
{ }
int main(int argc,char **argv)
{
foo1(argv);
char *p;
foo2(p);
return ;
}

为什么第一个调用有警告,第二个没有?

要解释这个问题,真是破费心机。

ANSI C 6.3.16.1节对于简单赋值这样描述:

两个操作数都是指向有限定符或者无限定符的相容类型的指针,左边指针所指向的类型必须具有右边指针所指向类型的全部限定符。

(在顶层const时不再适用!)

函数调用时,实参传递给形参,相当于赋值操作。

当第一次阅读到这个问题时,我是没有理解透彻的,《c专家编程》对这里的描述也是模棱两可,直到学习了c++之后,才算明白。

先看《c专家编程》上对这里的描述:

正是因为看了这本书,在学习c++的时候,刚开始一直很疑惑,为什么c++这里和c语言不一样,到后来,我明白了,是《c专家编程》这里讲解还是不够。对于上面的描述,我们做如下测试:

    char *cp;
char * const p="abc";
cp=p;

这样的赋值不会有警告,是不是和《c专家编程》描述有出入呢?在c++的学习中,我知道了,顶层const在赋值时会被忽略,在C语言中,也是同样的道理。所以,多多阅读书籍才能更好的提高。回到之前的话题,char *赋值给const char *不会有任何警告,证明它们是相容的,那为什么char ** 赋值给const char **就会有警告呢?

ANSI C 并没有对上述情况加以解释说明,但是在6.1.2.5节中这样讲述:

const float * 类型并不是一个有限定符的类型(在我当初阅读的时候,觉得这里和她上面的举例是矛盾的,这里没有限定符,那上面那个例子不就是说自身有一个const限定符吗?后来我发现,上面所说的限定符仅仅是指const,也并没有说是指针的呀!)---它的类型是“指向一个具有const限定符的float类型的指针”,也就是说const限定符修饰的是指针所指向的类型,而不是指针本身。

类似地,const char **也是一个没有限定符修饰的指针类型(注意这里的描述是对于指针类型的)。它的类型是“指向有const限定符的char类型的指针的指针”。由于它和char **一样都是没有限定符的指针类型,但它们指向的类型不一样,一个指向const char * ,一个指向char * 。因此它们是不相容的。虽然char *可以赋值给const cahr *,但是相容性不能传递,那么const char **与char **还是不相容。

阅读ANSI C,寻找乐趣和裨益——const char **与char **为何不兼容的更多相关文章

  1. 【转】深入理解const char*p,char const*p,char *const p,const char **p,char const**p,char *const*p,char**const p

    一.可能的组合: (1)const char*p (2)char const*p (3)char *const p(4)const char **p (5)char const**p (6)char ...

  2. 【C++】int、const char*、char*、char、string之间的转换

    #include "stdafx.h" #include<string> #include<vector> #include<iostream> ...

  3. 字符串复制char *strcpy(char* dest, const char *src);

    ⒈strcpy的实现代码 char * strcpy(char * strDest,const char * strSrc) { if ((NULL==strDest) || (NULL==strSr ...

  4. [转载] 已知strcpy的函数原型:char *strcpy(char *strDest, const char *strSrc),编写函数 strcpy(C++版)

    已知strcpy的函数原型:char *strcpy(char *strDest, const char *strSrc)其中strDest 是目的字符串,strSrc 是源字符串.不调用C++/C ...

  5. const char*、char*、char* const、char[]、string的区别

    1.const char* p: p is a pointer to const char(char const* p 一样)   意思就是不能通过p指针来修改p指向的内容(但是内容可以修改). 2. ...

  6. C 和 OC 字符串转换 NSString 和 char * 转换 const char* 与 char *

    #import <Foundation/Foundation.h> int main(int argc, const char * argv[]) { char *s = "He ...

  7. 无法从“const char *”转换为“char *”

    写了如下的一段代码: const char *str; char *p=str; 提示错误: const char* 不能用于初始化char *类型的实体.这是为什么?我想应该是const char ...

  8. string、const char*、 char* 、char[]相互转换

    转化总结如下: 目标格式 源格式 string const char* char* char[] string NULL const char*=string.c_str(); const char* ...

  9. string、const char*、 char* 、char[]相互转换(待整理)

    string.const char*. char* .char[]相互转换(全) https://blog.csdn.net/rongrongyaofeiqi/article/details/5244 ...

随机推荐

  1. 获取泛型类对应的class类型

    自己写来备忘的,如有错误,请指正! public class Demo<T> { private Class<T> clazz; public Demo() { Paramet ...

  2. shell之“>/dev/null 2>&1”

    shell之“>/dev/null 2>&1” http://ixdba.blog.51cto.com/2895551/526442 今天在自己的一个技术群中又被问道了这么一个问题 ...

  3. java 和 C 代码运行效率的比较(整理)

    最近和朋友无意间讨论起了 有关java 和C 的 效率问题, (我是java 推介者, 他是 c 语言推介者, 他做的是嵌入式) 故,想通过网络查询一下, 总结一下,两者到底效率如何,其有何差异,原因 ...

  4. poj 2187 Beauty Contest , 旋转卡壳求凸包的直径的平方

    旋转卡壳求凸包的直径的平方 板子题 #include<cstdio> #include<vector> #include<cmath> #include<al ...

  5. Python 的 if __name__ == '__main__'

    Python 文件 最后部分会有: if __name__ == '__main__': TestRLSO()……………… 1)首先,这是一个判断语句. 表示执行的是此代码所在的文件.如果这个文件是作 ...

  6. 调试解决iOS内存泄漏

    这里讲述在没有ARC的情况下,如何使用Instruments来查找程序中的内存泄露,以及NSZombieEnabled设置的使用. 本文假设你已经比较熟悉Obj-C的内存管理机制. 实验的开发环境:X ...

  7. linux 常用awk命令

    linux awk命令详解awk是一个强大的文本分析工具,相对于grep的查找,sed的编辑,awk在其对数据分析并生成报告时,显得尤为强大.简单来说awk就是把文件逐行的读入,以空格为默认分隔符将每 ...

  8. 使用WinSCP连接linux

    1.运行WinSCP工具,新建站点,输入主机名.用户名.密码,点击“保存(S)...”按钮 2.点击“确定”按钮,保存站点信息 3.选择左侧列表中的“root@192.168.67.2”这一项,然后点 ...

  9. 【Linux】目录配置

    为什么每套Linux distributions的配置文件.执行文件.每个目录内放置的文件其实都差不多?因为有一套需要依据的标准!我们底下就来瞧一瞧. 因为利用Linux来开发产品或distribut ...

  10. RMAN备份时报“ORA-19504: failed to create file”和“ORA-27038: created file already exists”

    RMAN> run { > allocate channel ch00 type disk; > backup format '/dbbackup/db_%T' database; ...