📄 constmismatch.html
字号:
<!DOCTYPE HTML PUBLIC "-//W3O//DTD W3 HTML 2.0//EN"><!-- This collection of hypertext pages is Copyright 1995-2005 by Steve Summit. --><!-- Content from the book "C Programming FAQs: Frequently Asked Questions" --><!-- (Addison-Wesley, 1995, ISBN 0-201-84519-9) is made available here by --><!-- permission of the author and the publisher as a service to the community. --><!-- It is intended to complement the use of the published text --><!-- and is protected by international copyright laws. --><!-- The on-line content may be accessed freely for personal use --><!-- but may not be published or retransmitted without explicit permission. --><!-- --><!-- this page built Sat Dec 24 21:47:46 2005 by faqproc version 2.7 --><!-- from source file ansi.sgml dated Wed Aug 11 00:43:45 2004 --><!-- corresponding to FAQ list version 4.0 --><html><!-- Mirrored from c-faq.com/ansi/constmismatch.html by HTTrack Website Copier/3.x [XR&CO'2008], Sat, 14 Mar 2009 07:58:55 GMT --><head><meta name=GENERATOR content="faqproc"><title>Question 11.10</title><link href="constptrconst.html" rev=precedes><link href="typedefconst.html" rel=precedes><link href="index.html" rev=subdocument></head><body bgcolor="#ffffff"><a href="constptrconst.html" rev=precedes><img src="../images/buttonleft.gif" alt="prev"></a><a href="index.html" rev=subdocument><img src="../images/buttonup.gif" alt="up"></a><a href="typedefconst.html" rel=precedes><img src="../images/buttonright.gif" alt="next"></a> <a href="../index-2.html"><img src="../images/buttontop.gif" alt="top/contents"></a><a href="../search.html"><img src="../images/buttonsrch.gif" alt="search"></a><hr><p><!-- qbegin --><h1>comp.lang.c FAQ list<font color=blue>·</font><!-- qtag -->Question 11.10</h1><p><font face=Helvetica size=8 color=blue><b>Q:</b></font>Why can't I pass a <TT>char **</TT> to a function which expects a<TT>const char **</TT>?</p><p><hr><p><font face=Helvetica size=8 color=blue><b>A:</b></font>You can use a pointer-to-T (for any type T) where apointer-to-const-T is expected.However,therule(an explicit exception)which permits slight mismatchesin qualified pointertypesis not applied recursively,but only at the top level.(<TT>const char **</TT> ispointer-to-pointer-to-const-char,and the exceptiontherefore does not apply.)</p><p>The reason that you cannot assign a<TT>char **</TT> value to a <TT>const char **</TT>pointer is somewhat obscure.Given that the <TT>const</TT> qualifier exists at all,the compiler would like to help you keep your promises not to modify <TT>const</TT> values.That's why you can assigna <TT>char *</TT> to a <TT>const char *</TT>,but not the other way around:it's clearly safe to ``add'' <TT>const</TT>-ness to a simple pointer,but it would be dangerous to take it away.However, suppose you performed the followingmore complicatedseries ofassignments:<pre> const char c = 'x'; /* 1 */ char *p1; /* 2 */ const char **p2 = &p1; /* 3 */ *p2 = &c; /* 4 */ *p1 = 'X'; /* 5 */</pre>In line 3,we assign a <TT>char **</TT> to a <TT>const char **</TT>.(The compiler should complain.)In line 4,we assign a <TT>const char *</TT> to a <TT>const char *</TT>;this is clearly legal.In line 5,we modify what a <TT>char *</TT> points to--this is supposed to be legal.However, <TT>p1</TT> ends up pointing to <TT>c</TT>,which is <TT>const</TT>.This came about in line 4,because <TT>*p2</TT> was really <TT>p1</TT>.This was set up in line 3,which is an assignment of a form that is disallowed,and this is exactly <em>why</em> line 3 is disallowed.</p><p>Assigning a <TT>char **</TT> to a <TT>const char **</TT>(as in line 3, and in the original question)is not immediately dangerous.But it sets up a situation in which <TT>p2</TT>'s promise--thatthe ultimately-pointed-to value won't be modified--cannotbe kept.</p><p>(C++has more complicated rulesfor assigning <TT>const</TT>-qualified pointerswhich let you make more kinds of assignmentswithout incurring warnings,but still protect against inadvertent attemptsto modify <TT>const</TT> values.C++ would still not allowassigning a <TT>char **</TT> to a <TT>const char **</TT>,but it would let you get away withassigning a <TT>char **</TT>to a <TT>const char * const *</TT>.)</p><p>In C,ifyou mustassign or passpointers which have qualifier mismatches atother than the first level of indirection,youmust use explicit casts(e.g. <TT>(const char **)</TT> in this case),although as always,the need for such a cast may indicate a deeper problemwhich the cast doesn't really fix.</p><p>References:ISO Sec. 6.1.2.6, Sec. 6.3.16.1, Sec. 6.5.3<br>H&S Sec. 7.9.1 pp. 221-2<br></p><!-- aend --><p><hr><a href="constptrconst.html" rev=precedes><img src="../images/buttonleft.gif" alt="prev"></a><a href="index.html" rev=subdocument><img src="../images/buttonup.gif" alt="up"></a><a href="typedefconst.html" rel=precedes><img src="../images/buttonright.gif" alt="next"></a> <a href="../questions.html"><img src="../images/buttontop.gif" alt="contents"></a><a href="../search.html"><img src="../images/buttonsrch.gif" alt="search"></a><br><!-- lastfooter --><a href="../about.html">about this FAQ list</a> <a href="../eskimo.html">about eskimo</a> <a href="../search.html">search</a> <a href="../feedback.html">feedback</a> <a href="copyright.html">copyright</a><p>Hosted by<a href="http://www.eskimo.com/"><img src="../../www.eskimo.com/img/link/eskitiny.gif" alt="Eskimo North"></a></body><!-- Mirrored from c-faq.com/ansi/constmismatch.html by HTTrack Website Copier/3.x [XR&CO'2008], Sat, 14 Mar 2009 07:58:55 GMT --></html>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -