在libidn的stringprep.h裡面,有這樣的聲明:
extern IDN_DLL_VAR const Stringprep_profiles stringprep_profiles[];<br />extern IDN_DLL_VAR const Stringprep_table_element stringprep_rfc3454_A_1[];
聲明的實現在c檔案裡面,例如profiles.c
Stringprep_profiles stringprep_profiles[] = {<br /> {"Nameprep", stringprep_nameprep},<br /> {"KRBprep", stringprep_kerberos5}, /* Deprecate? */<br /> {"Nodeprep", stringprep_xmpp_nodeprep},<br /> {"Resourceprep", stringprep_xmpp_resourceprep},<br /> {"plain", stringprep_plain}, /* sasl-anon-00. */<br /> {"trace", stringprep_trace}, /* sasl-anon-01,02,03. */<br /> {"SASLprep", stringprep_saslprep},<br /> {"ISCSIprep", stringprep_iscsi}, /* Obsolete. */<br /> {"iSCSI", stringprep_iscsi}, /* IANA. */<br /> {NULL, NULL}<br />};
libidn是可以在vs裡面編譯通過的,我有一個c++項目要用libidn,但在編譯時間會報錯,
error C2133: 'stringprep_profiles' : unknown size
在MSDN裡面,對error C2133的說明為:http://msdn.microsoft.com/en-us/library/c13wk277(VS.71).aspx
An unsized array is declared as a member of a class, structure, union, or enumeration. The /Za (ANSI C) option does not allow unsized member arrays. The following sample generates C2133: // C2133.cpp// compile with: /Zastruct X{ int a[0]; // C2133, unsized array};int main(){} |
如果你將stringprep.h的數組聲明改為:
extern IDN_DLL_VAR const Stringprep_profiles* stringprep_profiles;
extern IDN_DLL_VAR const Stringprep_table_element* stringprep_rfc3454_A_1;
可以編過,但運行時是錯誤的,stringprep_profiles指向的0x00000003。
這是為什麼呢?不至於要將所有的數組都指定大小吧。
先看一個簡化的例子,下面的例子是可以編過的,並且運行正常
//f:/My Documents/Visual Studio 2008/Projects/TestProject/ArrayStruct/ArrayDefine.h<br />#pragma once<br />#ifdef __cplusplus<br />extern "C"<br />{<br />#endif<br />typedef struct{<br /> int i;<br /> int j;<br />} A;<br />//const A test[];<br />A test[];<br />#ifdef __cplusplus<br />}<br />#endif
//f:/My Documents/Visual Studio 2008/Projects/TestProject/ArrayStruct/ArrayDef.c<br />#include "ArrayDefine.h"<br />//const A test[]=<br />A test[]=<br />{<br /> {<br /> 1,2<br /> },<br /> {<br /> 3,4<br /> }<br />};
//f:/My Documents/Visual Studio 2008/Projects/TestProject/ArrayStruct/ArrayStruct.cpp<br />#include "stdafx.h"<br />#include "ArrayDefine.h"<br />int _tmain(int argc, _TCHAR* argv[])<br />{<br /> printf("%d,%d/n",test[0].i,test[0].j);<br /> return 0;<br />}
如果在數組前面加一個const,如注釋掉的語句,這時就會編譯不過去。
如果你加了const並且將ArrayStruct.cpp的檔案名稱改為ArrayStruct.c也可以編過去並正常運行。
通過上面的例子可以看出c++和c裡面對const和數組聲明的不同處理了。