|
|
|
鐘舵€佹満(2)
o 鐢ㄦ湁絀風姸鎬佹満瑙d竴閬撻潰璇曢銆?/p>
鍒氭瘯涓氱殑鏃跺€欙紝鎴戝埌涓€瀹跺浼侀潰璇曪紝闈㈣瘯棰橀噷鏈夎繖鏍蜂竴閬撻錛?/p>
緇熻涓€綃囪嫳鏂囨枃绔犻噷鐨勫崟璇嶄釜鏁般€?/p>
鏈夊縐嶆柟娉曞彲浠ヨВ榪欓亾棰橈紝榪欓噷鎴戜滑閫夋嫨鐢ㄦ湁絀風姸鎬佹満鏉ヨВ錛屽仛娉曞涓嬶細
鍏堟妸榪欑瘒鑻辨枃鏂囩珷璇誨叆鍒頒竴涓紦鍐插尯閲岋紝璁╀竴涓寚閽堜粠緙撳啿鍖虹殑澶撮儴涓€鐩寸Щ鍒扮紦鍐插尯鐨勫熬閮紝鎸囬拡浼氬浜庝袱縐嶇姸鎬侊細“鍗曡瘝鍐?#8221;鎴?#8220;鍗曡瘝澶?#8221;錛屽姞涓婂悗闈㈡彁鍒扮殑鍒濆鐘舵€佸拰鎺ュ彈鐘舵€侊紝灝辨槸鏈夌┓鐘舵€佹満鐨勭姸鎬侀泦銆傜紦鍐插尯涓殑瀛楃闆嗗悎灝辨槸鏈夌┓鐘舵€佹満鐨勫瓧姣嶈〃銆?/p>
濡傛灉褰撳墠鐘舵€佷負“鍗曡瘝鍐?#8221;錛岀Щ鍒版寚閽堟椂錛屾寚閽堟寚鍚戠殑瀛楃鏄潪鍗曡瘝瀛楃(濡傛爣鐐瑰拰絀烘牸)錛岄偅鐘舵€佷細浠?#8220;鍗曡瘝鍐?#8221;杞崲鍒?#8220;鍗曡瘝澶?#8221;銆傚鏋滃綋鍓嶇姸鎬佷負“鍗? 璇嶅”錛?縐誨埌鎸囬拡鏃訛紝鎸囬拡鎸囧悜鐨勫瓧絎︽槸鍗曡瘝瀛楃(濡傚瓧姣?錛岄偅鐘舵€佷細浠?#8220;鍗曡瘝澶?#8221;杞崲鍒?#8220;鍗曡瘝鍐?#8221;銆傝繖浜涜漿鎹㈣鍒欏氨鏄姸鎬佽漿鎹㈠嚱鏁般€?/p>
鎸囬拡鎸囧悜緙撳啿鍖虹殑澶撮儴鏃舵槸鍒濆鐘舵€併€?/p>
鎸囬拡鎸囧悜緙撳啿鍖虹殑灝鵑儴鏃舵槸鎺ュ彈鐘舵€併€?/p>
姣忔褰撶姸鎬佷粠“鍗曡瘝鍐?#8221;杞崲鍒?#8220;鍗曡瘝澶?#8221;鏃訛紝鍗曡瘝璁℃暟澧炲姞涓€銆?br /> 榪欎釜鏈夌┓鐘舵€佹満鐨勫浘褰㈣〃紺哄涓嬶細
涓嬮潰鎴戜滑鐪嬬湅紼嬪簭鎬庝箞鍐欙細
int count_word(const char* text)
{
/*瀹氫箟鍚勭鐘舵€侊紝鎴戜滑涓嶅叧蹇冩帴鍙楃姸鎬侊紝榪欓噷鍙互涓嶇敤瀹氫箟銆?/
enum _State
{
STAT_INIT,
STAT_IN_WORD,
STAT_OUT_WORD,
}state = STAT_INIT;
int count = 0;
const char* p = text;
/*鍦ㄤ竴涓驚鐜腑錛屾寚閽堜粠緙撳啿鍖哄ご縐誨姩緙撳啿鍖哄熬*/
for(p = text; *p != '\0'; p++)
{
switch(state)
{
case STAT_INIT:
{
if(IS_WORD_CHAR(*p))
{
/*鎸囬拡鎸囧悜鍗曡瘝瀛楃錛岀姸鎬佽漿鎹負鍗曡瘝鍐?/
state = STAT_IN_WORD;
}
else
{
/*鎸囬拡鎸囧悜闈炲崟璇嶅瓧絎︼紝鐘舵€佽漿鎹負鍗曡瘝澶?/
state = STAT_OUT_WORD;
}
break;
}
case STAT_IN_WORD:
{
if(!IS_WORD_CHAR(*p))
{
/*鎸囬拡鎸囧悜闈炲崟璇嶅瓧絎︼紝鐘舵€佽漿鎹負鍗曡瘝澶栵紝澧炲姞鍗曡瘝璁℃暟*/
count++;
state = STAT_OUT_WORD;
}
break;
}
case STAT_OUT_WORD:
{
if(IS_WORD_CHAR(*p))
{
/*鎸囬拡鎸囧悜鍗曡瘝瀛楃錛岀姸鎬佽漿鎹負鍗曡瘝鍐?/
state = STAT_IN_WORD;
}
break;
}
default:break;
}
}
if(state == STAT_IN_WORD)
{
/*濡傛灉鐢卞崟璇嶅唴榪涘叆鎺ュ彈鐘舵€侊紝澧炲姞鍗曡瘝璁℃暟*/
count++;
}
return count;
}
鐢ㄧ姸鎬佹満鏉ヨВ榪欓亾棰樼洰錛屾€濊礬娓呮櫚錛岀▼搴忕畝鍗曪紝涓嶆槗鍑洪敊銆?/p>
榪欓亾棰樼洰鍙槸涓轟簡灞曠ず涓€浜涘鎶€娣閥錛岃繕鏄湁涓€浜涘疄闄呯敤澶勫憿錛熷洖絳旇繖涓棶棰樹箣鍓嶏紝鎴戜滑鍏堝涓婇潰鐨勭▼搴忓仛鐐規墿灞曪紝涓嶅彧鏄粺璁″崟璇嶇殑涓暟錛岃€屼笖瑕佸垎紱誨嚭閲岄潰鐨勬瘡涓崟璇嶃€?/p>
int word_segmentation(const char* text, OnWordFunc on_word, void* ctx)
{
enum _State
{
STAT_INIT,
STAT_IN_WORD,
STAT_OUT_WORD,
}state = STAT_INIT;
int count = 0;
char* copy_text = strdup(text);
char* p = copy_text;
char* word = copy_text;
for(p = copy_text; *p != '\0'; p++)
{
switch(state)
{
case STAT_INIT:
{
if(IS_WORD_CHAR(*p))
{
word = p;
state = STAT_IN_WORD;
}
break;
}
case STAT_IN_WORD:
{
if(!IS_WORD_CHAR(*p))
{
count++;
*p = '\0';
on_word(ctx, word);
state = STAT_OUT_WORD;
}
break;
}
case STAT_OUT_WORD:
{
if(IS_WORD_CHAR(*p))
{
word = p;
state = STAT_IN_WORD;
}
break;
}
default:break;
}
}
if(state == STAT_IN_WORD)
{
count++;
on_word(ctx, word);
}
free(copy_text);
return count;
}
鐘舵€佹満涓嶅彉錛屽彧鏄湪鐘舵€佽漿鎹㈡椂錛屽仛鏄簨鎯呬笉涓€鏍楓€傝繖閲屼粠“鍗曡瘝鍐?#8221;杞崲鍒板叾瀹冪姸鎬佹椂錛屽鍔犲崟璇嶈鏁幫紝騫跺垎紱誨嚭褰撳墠鐨勫崟璇嶃€傝嚦浜庢嬁鍒嗙鍑虹殑鍗曡瘝鏉ュ仛浠€涔堬紝鐢變紶鍏ョ殑鍥炶皟鍑芥暟鍐沖畾錛屾瘮濡傚彲浠ョ敤鏉ョ粺璁℃瘡涓崟璇嶅嚭鐜扮殑棰戠巼銆?/p>
浣嗗鏋滆璁鴻繕鏄檺浜庤嫳鏂囨枃绔狅紝榪欎釜紼嬪簭鐨勬剰涔変粛鐒朵笉澶э紝鐜板湪鏉ュ仛榪涗竴姝ユ墿灞曘€傛垜浠€冭檻鐨勬枃鏈笉鍐嶆槸鑻辨枃鏂囩珷錛岃€屾槸涓€浜涙枃鏈暟鎹紝榪欎簺鏁版嵁鐢變竴浜涘垎闅旂鍒嗗紑錛屾垜浠妸鏁版嵁縐頒負token錛岀幇鍦ㄦ垜浠鎶婅繖浜泃oken鍒嗙鍑烘潵銆?/p>
typedef void (*OnTokenFunc)(void* ctx, int index, const char* token);
#define IS_DELIM(c) (strchr(delims, c) != NULL)
int parse_token(const char* text, const char* delims, OnTokenFunc on_token, void* ctx)
{
enum _State
{
STAT_INIT,
STAT_IN,
STAT_OUT,
}state = STAT_INIT;
int count = 0;
char* copy_text = strdup(text);
char* p = copy_text;
char* token = copy_text;
for(p = copy_text; *p != '\0'; p++)
{
switch(state)
{
case STAT_INIT:
case STAT_OUT:
{
if(!IS_DELIM(*p))
{
token = p;
state = STAT_IN;
}
break;
}
case STAT_IN:
{
if(IS_DELIM(*p))
{
*p = '\0';
on_token(ctx, count++, token);
state = STAT_OUT;
}
break;
}
default:break;
}
}
if(state == STAT_IN)
{
on_token(ctx, count++, token);
}
on_token(ctx, -1, NULL);
free(copy_text);
return count;
}
鐢ㄥ垎闅旂鍒嗛殧鐨勬枃鏈暟鎹湁寰堝錛屽錛?/p>
鐜PATH錛屽畠鐢?#8216;:’鍒嗗紑鐨勫涓礬寰勭粍鎴愩€傚錛?br /> /usr/lib/qt-3.3/bin:/usr/kerberos/bin:/backup/tools/jdk1.5.0_18/bin/:/usr/lib/ccache:/usr/local/bin:/bin:/usr/bin:/home/lixianjing/bin
鏂囦歡鍚嶏紝瀹冪敱‘/’鍒嗗紑鐨勮礬寰勭粍鎴愩€傚錛?br /> /usr/lib/qt-3.3/bin
URL涓殑鍙傛暟錛屽畠‘&’鍒嗗紑鐨勫涓猭ey/value瀵圭粍鎴愩€?br /> hl=zh-CN&q=limodev&btnG=Google+鎼滅儲&meta=&aq=f&oq=
鎵€鏈夎繖浜涙暟鎹兘鍙互鐢ㄤ笂闈㈢殑鍑芥暟澶勭悊錛屾墍浠ヨ繖涓皬鍑芥暟鏄鍏峰疄鐢ㄤ環鍊肩殑銆?/p>
鐘舵€佹満(1)
o 鏈夌┓鐘舵€佹満鐨勫艦寮忓畾涔?/p>
鏈夌┓鐘舵€佹満鏄竴涓簲鍏冪粍 (Q錛?#931;錛?#948;錛宷0錛孎)錛屽叾涓細
Q鏄竴涓湁絀烽泦鍚堬紝縐頒負鐘舵€侀泦銆?br />
Σ鏄竴涓湁絀烽泦鍚堬紝縐頒負瀛楁瘝琛ㄣ€?br />
δ: Q xΣ飪燪縐頒負鐘舵€佽漿縐誨嚱鏁般€?br />
q0 鏄垵濮嬬姸鎬併€?br />
F 鏄帴鍙楃姸鎬侀泦銆?/p>
鏁欑涔︿笂鏄繖鏍峰畾涔夋湁絀瘋嚜鍔ㄦ満鐨勶紝榪欎釜褰㈠紡瀹氫箟綺劇‘鐨勬弿榪頒簡鏈夌┓鐘舵€佹満鐨勫惈涔夈€備絾鏄ぇ閮ㄥ垎浜?鍖呮嫭鎴戣嚜宸?絎竴嬈$湅鍒板畠鏃訛紝鍙嶅鐨勮涓婂嚑閬嶏紝浠嶇劧涓嶇煡閬撳畠鍦ㄨ浠€涔堛€傚垢濂介€氳繃涓€浜涘疄渚嬶紝鎴戜滑鍙互寰堝鏄撴槑鐧芥湁絀風姸鎬佹満鐨勫師鐞嗐€?/p>
鑷姩闂ㄦ槸涓€涓吀鍨嬬殑鏈夌┓鐘舵€佹満錛?/p>
瀹冩湁“寮€”鍜?#8220;鍏?#8221;涓ょ鐘舵€侊紝榪欏氨鏄畠鐨勭姸鎬侀泦錛屼篃灝辨槸涓婇潰鎵€璇寸殑Q銆?/p>
浜哄彲浠ヤ粠鑷姩闂ㄨ繘鏉ユ垨鍑哄幓錛屽綋浜鴻繘鏉ユ垨鍑哄幓鐨勬椂鍊欙紝鑷姩闂ㄤ細鑷姩鎵撳紑錛屽鏋滃湪瑙勫畾鐨勬椂闂村唴娌℃湁浜鴻繘鍑猴紝鑷姩闂ㄤ細鑷姩鍏充笂銆備漢鐨勮繘鏉ャ€佸嚭鍘誨拰瓚呮椂涓変釜浜嬩歡鏄嚜鍔ㄩ棬鐨勫瓧姣嶈〃錛屼篃灝辨槸涓婇潰鎵€璇寸殑Σ銆傝€岃嚜鍔ㄩ棬鍦ㄥ綋鍓嶇姸鎬佷笅錛屽浜嬩歡鐨勫搷搴旓紝浼氬紩璧風姸鎬佺殑鍙樺寲錛岃繖灝辨槸鐘舵€佽漿鎹㈠嚱鏁幫紝涔熷氨鏄笂闈㈡墍璇寸殑δ銆?/p>
鑷姩闂ㄥ垰瀹夎濂界殑鏃跺€欙紝鎴戜滑鍙互璁や負瀹冩槸鍏充笂鐨勶紝鎵€浠ュ叧闂姸鎬佹槸鑷姩闂ㄧ殑鍒濆鐘舵€併€?/p>
鍦ㄧ悊鎯蟲儏鍐典笅錛岃嚜鍔ㄩ棬浼氫竴鐩磋繍琛岋紝鎵€浠ュ畠娌℃湁鎺ュ彈鐘舵€侊紝鎺ュ彈鐘舵€侀泦F鏄┖闆嗐€?/p>
鏈夌┓鐘舵€佹満鐨勫艦寮忓畾涔夊緢綺劇‘錛屾枃瀛楁弿榪版瘮杈冮€氫織錛岃€屽浘褰㈣〃紺哄垯姣旇緝鐩磋銆傞€氱敤寤烘ā璇█錛圲ML錛夐噷鐨勭姸鎬佸浘鏄姸鎬佹満鐨勫父鐢ㄥ浘褰㈣〃紺烘柟娉曘€傜畝鍗曠殑鐘舵€佸浘鍖呮嫭涓€浜涚姸鎬侊紝鐢ㄥ渾瑙掓柟妗嗚〃紺猴紝閲岄潰鏈夌姸鎬佺殑鍚嶇О銆傜姸鎬佷箣闂寸殑杞崲錛岀敤綆ご琛ㄧず錛屼笂闈㈠彲浠ュ姞杞崲鏉′歡銆傝嚜鍔ㄩ棬鐨勭姸鎬佹満鍙互鐢ㄤ笅鍥捐〃紺猴細
鏈夌┓鐘舵€佹満寰堢畝鍗曪紝鍦ㄧ敓媧諱腑鍙互鎵懼嚭寰堝榪欐牱鐨勪緥瀛愩€備絾鏄暀縐戜功閲岃寰楀お澶嶆潅浜嗭紝涓€浼氬効璇佹槑紜畾鎬ф湁絀風姸鎬佹満鍜岄潪紜畾鎬ф湁絀風姸鎬佹満鐨勭瓑浠鋒€э紝涓€浼氬効璇佹槑姝e垯琛ㄨ揪寮忕殑姝e垯榪愮畻鏄皝闂殑錛屼竴浼氬効鍙堟潵涓車寮曠悊銆傝姳浜嗗緢闀挎椂闂達紝鎴戞墠鏄庣櫧榪欎簺鍘熺悊錛屼絾涓ゅ勾涔嬪悗錛屾垜鍙堟妸瀹冧滑蹇樺緱涓€騫蹭簩鍑€銆?/p>
涓昏鍘熷洜鏄伐浣滀腑娌℃湁鏈轟細榪愮敤瀹冧滑錛岃繖浜涚悊璁虹殑璇佹槑浜庣紪紼嬫病鏈夊お澶х敤澶勶紝涓嶈繃鐘舵€佹満鏈韓鍗存槸鏂囨湰澶勭悊鍒╁櫒錛岀敱浜庣▼搴忓憳鍦ㄥ緢澶氬満鍚堜笅閮芥槸鍦ㄤ笌鏂囨湰鏁版嵁鎵撲氦閬擄紝鎵€浠ョ姸鎬佹満鏄▼搴忓憳蹇呭鐨勫伐鍏蜂箣涓€銆傝繖閲屾垜浠皢涓€璧峰涔犲浣曠敤鐘舵€佹満鏉ュ鐞嗘枃鏈暟鎹紝鍚庨潰鎴戜滑涔熶細鎻愬埌鐘舵€佹満鐨勫叾瀹冪敤閫旓紝涓嶈繃涓嶆槸鏈妭鐨勯噸鐐廣€?br />
鏂囩珷鍑哄錛?a >http://www.limodev.cn/blog
浣滆€呰仈緋繪柟寮忥細鏉庡厛闈?<xianjimli at hotmail dot com>
Builder妯″紡
鍓嶉潰鎴戜滑瀛︿範浜嗙姸鎬佹満錛屽茍鍒╃敤瀹冩潵瑙f瀽鍚勭鏍煎紡鐨勬枃鏈暟鎹€傝В鏋愯繃紼嬫妸綰挎€х殑鏂囨湰鏁版嵁杞崲鎴愪竴浜涘熀鏈殑閫昏緫鍗曞厓錛屼絾榪欓€氬父鍙槸浠誨姟鐨勪竴閮ㄥ垎錛屾帴涓嬫潵鎴戜滑榪樿瀵硅繖浜涜В鏋愬嚭鏉ョ殑鏁版嵁榪涗竴姝ュ鐞嗐€傚浜庣壒瀹氭牸寮忕殑鏂囨湰鏁版嵁錛屽畠鐨勮В鏋愯繃紼嬫槸涓€鏍風殑錛屼絾鏄瑙f瀽鍑烘潵鐨勬暟鎹殑澶勭悊鍗存槸澶氱澶氭牱鐨勩€備負浜嗚瑙f瀽榪囩▼鑳借閲嶇敤錛屽氨闇€瑕佹妸鏁版嵁鐨勮В鏋愬拰鏁版嵁鐨勫鐞嗗垎寮€銆?/p>
鐜板湪鎴戜滑鍥炶繃澶存潵鐪嬩竴涓嬪墠闈㈠啓鐨勫嚱鏁皃arse_token錛岃繖涓嚱鏁版妸鐢ㄥ垎闅旂鍒嗛殧鐨勬枃鏈暟鎹紝鍒嗙鍑轟竴涓竴涓殑token銆?/p>
parse_token鐨勫嚱鏁板師鍨嬪涓嬶細
typedef void (*OnTokenFunc)(void* ctx, int index, const char* token);
int parse_token(const char* text, const char* delims, OnTokenFunc on_token, void* ctx)
parse_token璐熻矗瑙f瀽鏁版嵁錛屼絾瀹冨茍涓嶅叧蹇冩暟鎹唬琛ㄧ殑鎰忎箟鍙婄敤閫斻€傚鏁版嵁鐨勮繘涓€姝ュ鐞嗙敱璋冪敤鑰呮彁渚涚殑鍥炶皟鍑芥暟鏉ュ畬鎴愶紝鍑芥暟 parse_token姣忚В鏋愬埌涓€涓猼oken錛屽氨璋冪敤榪欎釜鍥炶皟鍑芥暟銆俻arse_token璐熻矗鏁版嵁鐨勮В鏋愶紝鍥炶皟鍑芥暟璐熻矗鏁版嵁鐨勫鐞嗭紝榪欐牱涓€鏉ワ紝鏁版嵁鐨勮В鏋愬拰鏁版嵁鐨勫鐞嗗氨鍒嗗紑浜嗐€?/p>
parse_token鍙互璁や負鏄疊uilder妯″紡鏈€鏈寸礌鐨勫簲鐢ㄣ€傜幇鍦ㄦ垜浠湅鐪婤uilder 妯″紡錛?/p>
Builder 妯″紡鐨勬剰鍥撅細灝嗕竴涓鏉傚璞$殑鏋勫緩涓庡畠鐨勮〃紺哄垎紱伙紝浣垮緱鍚屾牱鐨勬瀯寤鴻繃紼嬪彲浠ュ垱寤轟笉鍚岀殑琛ㄧず銆?#8220;鏋勫緩”鍏跺疄灝辨槸鍓嶉潰鐨勮В鏋愯繃紼嬶紝鑰?#8220;琛ㄧず”灝辨槸鍓嶉潰璇寸殑瀵規暟鎹殑澶勭悊銆?/p>
瀵硅薄鍏崇郴錛?br />
涓婇潰鐨刾arse_token涓庤繖閲岀殑Director瀵瑰簲銆?/p>
涓婇潰鐨勫洖璋冨嚱鏁頒笌榪欓噷鐨凚uilder瀵瑰簲銆?/p>
鍏蜂綋鐨勫洖璋冨嚱鏁頒笌榪欓噷鐨凜oncreteBuilder瀵瑰簲銆?/p>
瀵規暟鎹鐞嗙殑緇撴灉灝辨槸Product銆?/p>
瀵硅薄鍗忎綔錛?br />
Client鏄痯arse_token鐨勮皟鐢ㄨ€呫€?/p>
鐢變簬parse_token鏄寜闈㈠悜榪囩▼鐨勬柟寮忚璁$殑錛屾墍浠oncreteBuilder鍜孌irector鐨勫垱寤哄彧鏄搴斾簬涓€浜涘垵濮嬪寲浠g爜銆?/p>
璋冪敤parse_token鐩稿綋浜庤皟鐢╝Director鐨凜onstruct鍑芥暟銆?/p>
璋冪敤鍥炶皟鍑芥暟鐩稿綋浜庤皟鐢╝ConcreteBuilder鐨凚uildPart鍑芥暟銆?/p>
鍥炶皟鍑芥暟鍙兘鎶婂鐞嗙粨鏋滃瓨鍦ㄥ畠鐨勫弬鏁癱tx涓紝GetResult鏄粠閲岄潰鑾峰彇緇撴灉錛岃繖鏄彲閫夌殑榪囩▼錛屼緷璧栦簬鍏蜂綋鍥炶皟鍑芥暟鎵€鍋氱殑宸ヤ綔銆?/p>
parse_token鐨勪緥瀛愮畝鍗曠洿鎺ワ紝瀵逛簬鐞嗚ВBuilder妯″紡鏈夎緝澶х殑甯姪錛屼笉榪囨瘯绔熷畠鏄潰鍚戣繃紼嬬殑銆傜幇鍦ㄦ垜浠互鍓嶉潰鐨刋ML瑙f瀽鍣ㄤ負渚嬫潵璇存槑Builder妯″紡錛岃櫧鐒舵垜浠殑浠g爜鏄敤C鍐欑殑錛屼絾瀹屽叏鏄敤闈㈠悜瀵硅薄鐨勬€濇兂鏉ヨ璁$殑銆侭uilder鏄竴涓帴鍙o紝鎴戜滑鍏堟妸瀹冨畾涔夊嚭鏉ワ細
struct _XmlBuilder;
typedef struct _XmlBuilder XmlBuilder;
typedef void (*XmlBuilderOnStartElementFunc)(XmlBuilder* thiz, const char* tag, const char** attrs);
typedef void (*XmlBuilderOnEndElementFunc)(XmlBuilder* thiz, const char* tag);
typedef void (*XmlBuilderOnTextFunc)(XmlBuilder* thiz, const char* text, size_t length);
typedef void (*XmlBuilderOnCommentFunc)(XmlBuilder* thiz, const char* text, size_t length);
typedef void (*XmlBuilderOnPiElementFunc)(XmlBuilder* thiz, const char* tag, const char** attrs);
typedef void (*XmlBuilderOnErrorFunc)(XmlBuilder* thiz, int line, int row, const char* message);
typedef void (*XmlBuilderDestroyFunc)(XmlBuilder* thiz);
struct _XmlBuilder
{
XmlBuilderOnStartElementFunc on_start_element;
XmlBuilderOnEndElementFunc on_end_element;
XmlBuilderOnTextFunc on_text;
XmlBuilderOnCommentFunc on_comment;
XmlBuilderOnPiElementFunc on_pi_element;
XmlBuilderOnErrorFunc on_error;
XmlBuilderDestroyFunc destroy;
char priv[1];
};
static inline void xml_builder_on_start_element(XmlBuilder* thiz, const char* tag, const char** attrs)
{
return_if_fail(thiz != NULL && thiz->on_start_element != NULL);
thiz->on_start_element(thiz, tag, attrs);
return;
}
static inline void xml_builder_on_end_element(XmlBuilder* thiz, const char* tag)
{
return_if_fail(thiz != NULL && thiz->on_end_element != NULL);
thiz->on_end_element(thiz, tag);
return;
}
...
(鍏跺畠inline鍑芥暟涓嶅垪鍦ㄨ繖閲屼簡)
XmlBuilder鎺ュ彛瑕佹眰瀹炵幇涓嬪垪鍑芥暟錛?/p>
on_start_element錛氳В鏋愬櫒瑙f瀽鍒頒竴涓搗濮婽AG鏃惰皟鐢ㄥ畠銆?br /> on_end_element錛氳В鏋愬櫒瑙f瀽鍒頒竴涓粨鏉烼AG鏃惰皟鐢ㄥ畠銆?br /> on_text錛氳В鏋愬櫒瑙f瀽鍒頒竴孌墊枃鏈椂璋冪敤瀹冦€?br /> on_comment錛氳В鏋愬櫒瑙f瀽鍒頒竴涓敞閲婃椂璋冪敤瀹冦€?br /> on_pi_element錛氳В鏋愬櫒瑙f瀽鍒頒竴涓鐞嗘寚浠ゆ椂璋冪敤瀹冦€?br /> on_error錛氳В鏋愬櫒閬囧埌閿欒鏃惰皟鐢ㄥ畠銆?br /> destroy錛氱敤閿€姣丅uilder瀵硅薄銆?/p>
on_start_element鍜宱n_end_element絳夊嚱鏁扮浉褰撲簬Builder妯″紡涓殑BuildPartX鍑芥暟銆?/p>
XML瑙f瀽鍣ㄧ浉褰撲簬Director錛屽湪鍓嶉潰鎴戜滑宸茬粡鍐欏ソ浜嗭紝涓嶈繃瀹冨瑙f瀽鍑烘潵鐨勬暟鎹病鏈夊仛浠諱綍澶勭悊銆傜幇鍦ㄦ垜浠瀹冨仛浜涗慨鏀癸紝璁╁畠璋冪敤XmlBuilder鐨勫嚱鏁般€?/p>
XML瑙f瀽鍣ㄥ澶栨彁渚涗笅闈㈠嚑涓嚱鏁幫細
o 鏋勯€犲嚱鏁般€?/p>
XmlParser* xml_parser_create(void);
o 涓簒mlParser璁劇疆builder瀵硅薄銆?/p>
void xml_parser_set_builder(XmlParser* thiz, XmlBuilder* builder);
o 瑙f瀽XML
void xml_parser_parse(XmlParser* thiz, const char* xml);
o 鏋愭瀯鍑芥暟
void xml_parser_destroy(XmlParser* thiz);
鍦ㄨВ鏋愭椂錛岃В鏋愬埌鐩稿簲鐨則ag錛屽氨璋冪敤XmlBuilder鐩稿簲鐨勫嚱鏁幫細
o 瑙f瀽鍒拌搗濮媡ag鏃惰皟鐢▁ml_builder_on_start_element
static void xml_parser_parse_start_tag(XmlParser* thiz)
{
enum _State
{
STAT_NAME,
STAT_ATTR,
STAT_END,
}state = STAT_NAME;
char* tag_name = NULL;
const char* start = thiz->read_ptr - 1;
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
char c = *thiz->read_ptr;
switch(state)
{
case STAT_NAME:
{
if(isspace(c) || c == '>' || c == '/')
{
tag_name = (char*)xml_parser_strdup(thiz, start, thiz->read_ptr - start);
state = (c != '>' && c != '/') ? STAT_ATTR : STAT_END;
}
break;
}
case STAT_ATTR:
{
xml_parser_parse_attrs(thiz, '/');
state = STAT_END;
break;
}
default:break;
}
if(state == STAT_END)
{
break;
}
}
tag_name = thiz->buffer + (size_t)tag_name;
/*瑙f瀽瀹屾垚錛岃皟鐢╞uilder鐨勫嚱鏁皒ml_builder_on_start_element銆?/
xml_builder_on_start_element(thiz->builder, tag_name, (const char**)thiz->attrs);
if(thiz->read_ptr[0] == '/')
{
/*濡傛灉tag浠?/'緇撴潫錛岃皟鐢╞uilder鐨勫嚱鏁皒ml_builder_on_end_element銆?/
xml_builder_on_end_element(thiz->builder, tag_name);
}
for(; *thiz->read_ptr != '>' && *thiz->read_ptr != '\0'; thiz->read_ptr++);
return;
}
o 瑙f瀽鍒扮粨鏉焧ag鏃惰皟鐢▁ml_builder_on_end_element
static void xml_parser_parse_end_tag(XmlParser* thiz)
{
char* tag_name = NULL;
const char* start = thiz->read_ptr;
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
if(*thiz->read_ptr == '>')
{
tag_name = thiz->buffer + xml_parser_strdup(thiz, start, thiz->read_ptr-start);
/*瑙f瀽瀹屾垚錛岃皟鐢╞uilder鐨勫嚱鏁皒ml_builder_on_end_element銆?/
xml_builder_on_end_element(thiz->builder, tag_name);
break;
}
}
return;
}
o 瑙f瀽鍒版枃鏈椂璋冪敤xml_builder_on_text
static void xml_parser_parse_text(XmlParser* thiz)
{
const char* start = thiz->read_ptr - 1;
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
char c = *thiz->read_ptr;
if(c == '<')
{
if(thiz->read_ptr > start)
{
/*瑙f瀽瀹屾垚錛岃皟鐢╞uilder鐨勫嚱鏁皒ml_builder_on_text銆?/
xml_builder_on_text(thiz->builder, start, thiz->read_ptr-start);
}
thiz->read_ptr--;
return;
}
else if(c == '&')
{
xml_parser_parse_entity(thiz);
}
}
return;
}
o 瑙f瀽鍒版敞閲婃椂璋冪敤xml_builder_on_comment
static void xml_parser_parse_comment(XmlParser* thiz)
{
enum _State
{
STAT_COMMENT,
STAT_MINUS1,
STAT_MINUS2,
}state = STAT_COMMENT;
const char* start = ++thiz->read_ptr;
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
char c = *thiz->read_ptr;
switch(state)
{
case STAT_COMMENT:
{
if(c == '-')
{
state = STAT_MINUS1;
}
break;
}
case STAT_MINUS1:
{
if(c == '-')
{
state = STAT_MINUS2;
}
else
{
state = STAT_COMMENT;
}
break;
}
case STAT_MINUS2:
{
if(c == '>')
{
/*瑙f瀽瀹屾垚錛岃皟鐢╞uilder鐨勫嚱鏁皒ml_builder_on_comment銆?/
xml_builder_on_comment(thiz->builder, start, thiz->read_ptr-start-2);
return;
}
}
default:break;
}
}
return;
}
o 瑙f瀽鍒板鐞嗘寚浠ゆ椂璋冪敤xml_builder_on_pi_element
static void xml_parser_parse_pi(XmlParser* thiz)
{
enum _State
{
STAT_NAME,
STAT_ATTR,
STAT_END
}state = STAT_NAME;
char* tag_name = NULL;
const char* start = thiz->read_ptr;
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
char c = *thiz->read_ptr;
switch(state)
{
case STAT_NAME:
{
if(isspace(c) || c == '>')
{
tag_name = (char*)xml_parser_strdup(thiz, start, thiz->read_ptr - start);
state = c != '>' ? STAT_ATTR : STAT_END;
}
break;
}
case STAT_ATTR:
{
xml_parser_parse_attrs(thiz, '?');
state = STAT_END;
break;
}
default:break;
}
if(state == STAT_END)
{
break;
}
}
tag_name = thiz->buffer + (size_t)tag_name;
/*瑙f瀽瀹屾垚錛岃皟鐢╞uilder鐨勫嚱鏁皒ml_builder_on_pi_element銆?/
xml_builder_on_pi_element(thiz->builder, tag_name, (const char**)thiz->attrs);
for(; *thiz->read_ptr != '>' && *thiz->read_ptr != '\0'; thiz->read_ptr++);
return;
}
浠庝笂闈㈢殑浠g爜鍙互鐪嬪嚭錛孹mlParser鍦ㄩ€傚綋鐨勬椂鍊欒皟鐢ㄤ簡XmlBuilder鐨勬帴鍙e嚱鏁幫紝鑷充簬XmlBuilder鍦ㄨ繖浜涘嚱鏁伴噷鍋氫粈涔堬紝瑕佺湅鍏蜂綋鐨凚uilder瀹炵幇浜嗐€?/p>
鍏堢湅涓€涓渶綆€鍗曠殑XmlBuilder瀹炵幇錛屽畠鍙槸鍦ㄥ睆騫曚笂鎵撳嵃鍑轟紶閫掔粰瀹冪殑鏁版嵁錛?/p>
o 鍒涘緩鍑芥暟
XmlBuilder* xml_builder_dump_create(FILE* fp)
{
XmlBuilder* thiz = (XmlBuilder*)calloc(1, sizeof(XmlBuilder));
if(thiz != NULL)
{
PrivInfo* priv = (PrivInfo*)thiz->priv;
thiz->on_start_element = xml_builder_dump_on_start_element;
thiz->on_end_element = xml_builder_dump_on_end_element;
thiz->on_text = xml_builder_dump_on_text;
thiz->on_comment = xml_builder_dump_on_comment;
thiz->on_pi_element = xml_builder_dump_on_pi_element;
thiz->on_error = xml_builder_dump_on_error;
thiz->destroy = xml_builder_dump_destroy;
priv->fp = fp != NULL ? fp : stdout;
}
return thiz;
}
鍜屽叾瀹冩帴鍙g殑鍒涘緩鍑芥暟涓€鏍鳳紝瀹冨彧鏄妸鎺ュ彛瑕佹眰鐨勫嚱鏁版寚閽堟寚鍒板叿浣撶殑瀹炵幇鍑芥暟涓娿€?/p>
o 瀹炵幇 on_start_element
static void xml_builder_dump_on_start_element(XmlBuilder* thiz, const char* tag, const char** attrs)
{
int i = 0;
PrivInfo* priv = (PrivInfo*)thiz->priv;
fprintf(priv->fp, "<%s", tag);
for(i = 0; attrs != NULL && attrs[i] != NULL && attrs[i + 1] != NULL; i += 2)
{
fprintf(priv->fp, " %s=\"%s\"", attrs[i], attrs[i + 1]);
}
fprintf(priv->fp, ">");
return;
}
o 瀹炵幇on_end_element
static void xml_builder_dump_on_end_element(XmlBuilder* thiz, const char* tag)
{
PrivInfo* priv = (PrivInfo*)thiz->priv;
fprintf(priv->fp, "\n", tag);
return;
}
o 瀹炵幇on_text
static void xml_builder_dump_on_text(XmlBuilder* thiz, const char* text, size_t length)
{
PrivInfo* priv = (PrivInfo*)thiz->priv;
fwrite(text, length, 1, priv->fp);
return;
}
o 瀹炵幇on_comment
static void xml_builder_dump_on_comment(XmlBuilder* thiz, const char* text, size_t length)
{
PrivInfo* priv = (PrivInfo*)thiz->priv;
fprintf(priv->fp, "\n");
return;
}
o 瀹炵幇on_pi_element
static void xml_builder_dump_on_pi_element(XmlBuilder* thiz, const char* tag, const char** attrs)
{
int i = 0;
PrivInfo* priv = (PrivInfo*)thiz->priv;
fprintf(priv->fp, "fp, " %s=\"%s\"", attrs[i], attrs[i + 1]);
}
fprintf(priv->fp, "?>\n");
return;
}
o 瀹炵幇on_error
static void xml_builder_dump_on_error(XmlBuilder* thiz, int line, int row, const char* message)
{
fprintf(stderr, "(%d,%d) %s\n", line, row, message);
return;
}
涓婇潰鐨刋mlBuilder瀹炵幇綆€鍗曪紝鑰屼笖鏈変竴瀹氱殑瀹炵敤浠峰€鹼紝鎴戜竴鑸兘浼氬厛鍐欒繖鏍蜂竴涓狟uilder銆傚畠涓嶄絾瀵逛簬璋冭瘯紼嬪簭鏈変笉灝忕殑甯姪錛岃€屼笖鍙紼嶅仛淇敼錛屽氨鍙互鎶婂畠鏀硅繘鎴愪竴涓編鍖栨暟鎹牸寮忕殑灝忓伐鍏鳳紝涓嶇鍘熷鏁版嵁鐨勬牸寮?褰撶劧瑕佸悎絎︾浉搴旂殑璇硶瑙勫垯)鏈夊涔憋紝浣犻兘鑳戒互涓€縐嶆瘮杈冨ソ鐪嬬殑鏂瑰紡鎵撳嵃鍑烘潵銆?/p>
涓嬮潰鎴戜滑鍐嶇湅涓€涓瘮杈冨鏉傜殑XmlBuilder鐨勫疄鐜幫紝瀹冩牴鎹帴鏀剁殑鏁版嵁鏋勫緩涓€媯礨ML鏍戙€?/p>
o 鍒涘緩鍑芥暟
XmlBuilder* xml_builder_tree_create(void)
{
XmlBuilder* thiz = (XmlBuilder*)calloc(1, sizeof(XmlBuilder));
if(thiz != NULL)
{
PrivInfo* priv = (PrivInfo*)thiz->priv;
thiz->on_start_element = xml_builder_tree_on_start_element;
thiz->on_end_element = xml_builder_tree_on_end_element;
thiz->on_text = xml_builder_tree_on_text;
thiz->on_comment = xml_builder_tree_on_comment;
thiz->on_pi_element = xml_builder_tree_on_pi_element;
thiz->on_error = xml_builder_tree_on_error;
thiz->destroy = xml_builder_tree_destroy;
priv->root = xml_node_create_normal("__root__", NULL);
priv->current = priv->root;
}
return thiz;
}
鍜屽叾瀹冩帴鍙g殑鍒涘緩鍑芥暟涓€鏍鳳紝瀹冨彧鏄妸鎺ュ彛瑕佹眰鐨勫嚱鏁版寚閽堟寚鍒板叿浣撶殑瀹炵幇鍑芥暟涓娿€傝繖閲岃繕鍒涘緩浜嗕竴涓牴緇撶偣__root__錛屼互淇濊瘉鏁存5鏍戝彧鏈変竴涓牴緇撶偣銆?/p>
o 瀹炵幇 on_start_element
static void xml_builder_tree_on_start_element(XmlBuilder* thiz, const char* tag, const char** attrs)
{
XmlNode* new_node = NULL;
PrivInfo* priv = (PrivInfo*)thiz->priv;
new_node = xml_node_create_normal(tag, attrs);
xml_node_append_child(priv->current, new_node);
priv->current = new_node;
return;
}
榪欓噷鍒涘緩浜嗕竴涓柊鐨勭粨鐐癸紝騫惰拷鍔犱負priv->current鐨勫瓙緇撶偣錛岀劧鍚庤priv->current鎸囧悜鏂扮殑緇撶偣銆?/p>
o 瀹炵幇 on_end_element
static void xml_builder_tree_on_end_element(XmlBuilder* thiz, const char* tag)
{
PrivInfo* priv = (PrivInfo*)thiz->priv;
priv->current = priv->current->parent;
assert(priv->current != NULL);
return;
}
榪欓噷鍙槸璁﹑riv->current鎸囧悜瀹冪殑鐖剁粨鐐廣€?/p>
o 瀹炵幇 on_text
static void xml_builder_tree_on_text(XmlBuilder* thiz, const char* text, size_t length)
{
XmlNode* new_node = NULL;
PrivInfo* priv = (PrivInfo*)thiz->priv;
new_node = xml_node_create_text(text);
xml_node_append_child(priv->current, new_node);
return;
}
榪欓噷鍒涘緩涓€涓枃鏈粨鐐癸紝 騫惰拷鍔犱負priv->current鐨勫瓙緇撶偣銆?/p>
o 瀹炵幇 on_comment
static void xml_builder_tree_on_comment(XmlBuilder* thiz, const char* text, size_t length)
{
XmlNode* new_node = NULL;
PrivInfo* priv = (PrivInfo*)thiz->priv;
new_node = xml_node_create_comment(text);
xml_node_append_child(priv->current, new_node);
return;
}
榪欓噷鍒涘緩涓€涓敞閲婄粨鐐癸紝 騫惰拷鍔犱負priv->current鐨勫瓙緇撶偣銆?/p>
o 瀹炵幇 on_pi_element
static void xml_builder_tree_on_pi_element(XmlBuilder* thiz, const char* tag, const char** attrs)
{
XmlNode* new_node = NULL;
PrivInfo* priv = (PrivInfo*)thiz->priv;
new_node = xml_node_create_pi(tag, attrs);
xml_node_append_child(priv->current, new_node);
return;
}
榪欓噷鍒涘緩涓€涓鐞嗘寚浠ょ粨鐐癸紝 騫惰拷鍔犱負priv->current鐨勫瓙緇撶偣銆?/p>
o 瀹炵幇on_error
static void xml_builder_tree_on_error(XmlBuilder* thiz, int line, int row, const char* message)
{
fprintf(stderr, "(%d,%d) %s\n", line, row, message);
return;
}
涓嬮潰鎴戜滑鍐嶇湅XmlNode鐨勬暟鎹粨鏋勫拰涓昏鍑芥暟錛?/p>
o 鏁版嵁緇撴瀯
typedef struct _XmlNode
{
XmlNodeType type;
union
{
char* text;
char* comment;
XmlNodePi pi;
XmlNodeNormal normal;
}u;
struct _XmlNode* parent;
struct _XmlNode* children;
struct _XmlNode* sibling;
}XmlNode;
type鍐沖畾浜嗙粨鐐圭殑綾誨瀷錛屽彲浠ユ槸澶勭悊鎸囦護(XML_NODE_PI)銆佹枃鏈?XML_NODE_TEXT)銆佹敞閲?XML_NODE_COMMENT)鎴栨櫘閫歍AG(XML_NODE_NORMAL)銆?/p>
鑱斿悎浣撶敤浜庡瓨鏀懼叿浣撶粨鐐逛俊鎭€?/p>
parent鎸囧悜鐖剁粨鐐廣€?/p>
children鎸囧悜絎竴涓瓙緇撶偣銆?/p>
sibling鎸囧悜涓嬩竴涓厔寮熺粨鐐廣€?/p>
o 鍒涘緩鏅€歍AG緇撶偣
XmlNode* xml_node_create_normal(const char* name, const char** attrs)
{
XmlNode* node = NULL;
return_val_if_fail(name != NULL, NULL);
if((node = calloc(1, sizeof(XmlNode))) != NULL)
{
int i = 0;
node->type = XML_NODE_NORMAL;
node->u.normal.name = strdup(name);
if(attrs != NULL)
{
for(i = 0; attrs[i] != NULL && attrs[i+1] != NULL; i += 2)
{
xml_node_append_attr(node, attrs[i], attrs[i+1]);
}
}
}
return node;
}
o 鍒涘緩澶勭悊鎸囦護緇撶偣
XmlNode* xml_node_create_pi(const char* name, const char** attrs)
{
XmlNode* node = NULL;
return_val_if_fail(name != NULL, NULL);
if((node = calloc(1, sizeof(XmlNode))) != NULL)
{
int i = 0;
node->type = XML_NODE_PI;
node->u.pi.name = strdup(name);
if(attrs != NULL)
{
for(i = 0; attrs[i] != NULL && attrs[i+1] != NULL; i += 2)
{
xml_node_append_attr(node, attrs[i], attrs[i+1]);
}
}
}
return node;
}
o 鍒涘緩鏂囨湰緇撶偣
XmlNode* xml_node_create_text(const char* text)
{
XmlNode* node = NULL;
return_val_if_fail(text != NULL, NULL);
if((node = calloc(1, sizeof(XmlNode))) != NULL)
{
node->type = XML_NODE_TEXT;
node->u.text = strdup(text);
}
return node;
}
o 鍒涘緩娉ㄩ噴緇撶偣
XmlNode* xml_node_create_comment(const char* comment)
{
XmlNode* node = NULL;
return_val_if_fail(comment != NULL, NULL);
if((node = calloc(1, sizeof(XmlNode))) != NULL)
{
node->type = XML_NODE_COMMENT;
node->u.comment = strdup(comment);
}
return node;
}
o 榪藉姞涓€涓厔寮熺粨鐐?/p>
XmlNode* xml_node_append_sibling(XmlNode* node, XmlNode* sibling)
{
return_val_if_fail(node != NULL && sibling != NULL, NULL);
if(node->sibling == NULL)
{
/*娌℃湁鍏勫紵緇撶偣錛岃鍏勫紵緇撶偣鎸囧悜sibling */
node->sibling = sibling;
}
else
{
/*鍚﹀垯錛屾妸sibling榪藉姞涓烘渶鍚庝竴涓厔寮熺粨鐐?/
XmlNode* iter = node->sibling;
while(iter->sibling != NULL) iter = iter->sibling;
iter->sibling = sibling;
}
/*璁╁厔寮熺粨鐐圭殑鐖剁粨鐐規寚鍚戣嚜宸辯殑鐖剁粨鐐?/
sibling->parent = node->parent;
return sibling;
}
o 榪藉姞涓€涓瓙緇撶偣
XmlNode* xml_node_append_child(XmlNode* node, XmlNode* child)
{
return_val_if_fail(node != NULL && child != NULL, NULL);
if(node->children == NULL)
{
/*娌℃湁瀛愮粨鐐癸紝璁╁瓙緇撶偣鎸囧悜child */
node->children = child;
}
else
{
/*鍚﹀垯錛屾妸child 榪藉姞涓烘渶鍚庝竴涓瓙緇撶偣*/
XmlNode* iter = node->children;
while(iter->sibling != NULL) iter = iter->sibling;
iter->sibling = child;
}
/*璁╁瓙緇撶偣鐨勭埗緇撶偣鎸囧悜鑷繁*/
child->parent = node;
return child;
}
鍥炲ご鍐嶇湅涓€涓媂mlParser錛孹mlBuilder鍙婂嚑涓叿浣撶殑XmlBuilder鐨勫疄鐜幫紝鎴戜滑鍙互鐪嬪埌錛屽畠浠殑瀹炵幇閮介潪甯哥畝鍗曪紝鍏跺疄榪欏畬鍏ㄥ緱鐩婁簬Builder妯″紡鐨勮璁℃柟娉曘€傚畠鍒╃敤鍒嗚€屾不涔嬬殑鎬濇兂錛屾妸鏁版嵁鐨勮В鏋愬拰鏁版嵁鐨勫鐞嗗垎寮€錛岄檷浣庝簡瀹炵幇鐨勫鏉傚害銆傚叾嬈″畠鍒╃敤浜嗘娊璞$殑鎬濇兂錛屼粠鑰屾暟鎹殑瑙f瀽鍙叧蹇冨鐞嗘暟鎹鐞嗙殑鎺ュ彛錛岃€屼笉鍏沖績鐨勫畠鐨勫疄鐜幫紝浣垮緱鏁版嵁瑙f瀽鍜屾暟鎹鐞嗗彲浠ョ嫭绔嬪彉鍖栥€?/p>
鍒嗚€屾不涔嬪拰鎶借薄鏄檷浣庡鏉傚害鏈€鏈夋晥鐨勬墜孌典箣涓€錛屽畠浠湪Builder妯″紡閲屽緱鍒頒簡寰堝ソ鐨勪綋鐜般€傚垵瀛﹁€呭簲璇ュ鑺變簺鏃墮棿鍘諱綋浼氥€?br />
鏂囩珷鍑哄錛?a >http://www.limodev.cn/blog
浣滆€呰仈緋繪柟寮忥細鏉庡厛闈?<xianjimli at hotmail dot com>
緋葷粺紼嬪簭鍛樻垚闀胯鍒?鏂囨湰澶勭悊(涓€)
鐘舵€佹満(4)
XML瑙f瀽鍣?/p>
XML錛圗xtensible Markup Language錛夊嵆鍙墿灞曟爣璁拌璦€錛屼篃鏄竴縐嶅父鐢ㄧ殑鏁版嵁鏂囦歡鏍煎紡銆傜浉瀵逛簬INI鏉ヨ錛屽畠瑕佸鏉傚緱澶氾紝INI鍙兘淇濆瓨綰挎€х粨鏋勭殑鏁版嵁錛岃€孹ML鍙互淇濆瓨鏍戝艦緇撴瀯鐨勬暟鎹€傚厛鐪嬩笅闈㈢殑渚嬪瓙錛?/p>
<?xml version="1.0" encoding="utf-8"?>
<mime-type xmlns="http://www.freedesktop.org/standards/shared-mime-info" type="all/all">
<!--Created automatically by update-mime-database. DO NOT EDIT!-->
<comment>all files and folders</comment>
</mime-type>
絎竴琛岀О涓哄鐞嗘寚浠?PI)錛屾槸緇欒В鏋愬櫒鐢ㄧ殑銆傝繖閲屽憡璇夎В鏋愬櫒錛屽綋鍓嶇殑XML鏂囦歡閬靛驚XML 1.0瑙勮寖錛屾枃浠跺唴瀹圭敤UTF-8緙栫爜銆?/p>
絎簩琛屾槸涓€涓搗濮婽AG錛孴AG鐨勫悕縐頒負mime-type銆傚畠鏈変袱涓睘鎬э紝絎竴涓睘鎬х殑鍚嶇О涓簒mlns錛屽€間負 http://www.freedesktop.org/standards/shared-mime-info銆傜浜屼釜灞炴€х殑鍚嶇О涓簍ype錛屽€間負 all/all銆?/p>
絎笁琛屾槸涓€涓敞閲娿€?/p>
絎洓琛屽寘鎷竴涓搗濮婽AG錛屼竴孌墊枃鏈拰緇撴潫TAG銆?/p>
絎簲琛屾槸涓€涓粨鏉烼AG銆?/p>
XML鏈韓鐨勬牸寮忎笉鏄湰鏂囩殑閲嶇偣錛屾垜浠笉璇︾粏璁ㄨ浜嗐€傝繖閲岀殑閲嶇偣鏄浣曠敤鐘舵€佹満瑙f瀽鏍煎紡澶嶆潅鐨勬暟鎹€?/p>
鎸夌収鍓嶉潰鐨勬柟娉曪紝鍏堟妸鏁版嵁璇誨叆鍒頒竴涓紦鍐插尯涓紝璁╀竴涓寚閽堟寚鍚戠紦鍐插尯鐨勫ご閮紝鐒跺悗縐誨姩鎸囬拡錛岀洿鍒版寚鍚戠紦鍐插尯鐨勫熬閮ㄣ€傚湪榪欎釜榪囩▼涓紝鎸囬拡鍙兘鎸囧悜錛氳搗濮婽AG錛岀粨鏉烼AG錛屾敞閲婏紝澶勭悊鎸囦護鍜屾枃鏈€傜敱姝ゆ垜浠畾涔夊嚭鐘舵€佹満鐨勪富瑕佺姸鎬侊細
1. 璧峰TAG鐘舵€?br /> 2. 緇撴潫TAG鐘舵€?br /> 3. 娉ㄩ噴鐘舵€?br /> 4. 澶勭悊鎸囦護鐘舵€?br /> 5. 鏂囨湰鐘舵€?/p>
鐢變簬璧峰TAG銆佺粨鏉烼AG銆佹敞閲婂拰澶勭悊鎸囦護閮藉湪瀛楃‘<’鍜?#8216;>’涔嬮棿錛屾墍浠ュ綋璇誨叆瀛楃‘<’鏃訛紝鎴戜滑榪樻棤娉曠煡閬撳綋鍓嶇殑鐘舵€侊紝涓轟簡渚夸簬澶勭悊錛屾垜浠紩鍏ヤ竴涓腑闂寸姸鎬侊紝縐頒負“灝忎簬鍙蜂箣鍚?#8221;鐨勭姸鎬併€傚湪璇誨叆瀛楃‘<’鍜?#8216;!’涔嬪悗錛岃繕瑕佽鍏ヤ袱涓?#8216;-’錛屾墠鑳界‘瀹氳繘鍏ユ敞閲婄姸鎬侊紝涓轟簡渚夸簬澶勭悊錛屽啀寮曞叆涓や釜涓棿鐘舵€?#8220;娉ㄩ噴鍓嶄竴”鍜?#8220;娉ㄩ噴鍓嶄簩”銆傚啀寮曞叆涓€涓?#8220;絀?#8221;鐘舵€侊紝琛ㄧず涓嶅湪涓婅堪浠諱綍鐘舵€佷腑銆?/p>
鐘舵€佽漿鎹㈠嚱鏁幫細
1. 鍦?#8220;絀?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;<’錛岃繘鍏?#8220;灝忎簬鍙蜂箣鍚?#8221;鐘舵€併€?br />
2. 鍦?#8220;絀?#8221;鐘舵€佷笅錛岃鍏ラ潪‘<’闈炵┖鐧界殑瀛楃錛岃繘鍏?#8220;鏂囨湰”鐘舵€併€?br />
3. 鍦?#8220;灝忎簬鍙蜂箣鍚?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;錛?#8217;錛岃繘鍏?#8220;娉ㄩ噴鍓嶄竴” 鐘舵€併€?br />
4. 鍦?#8220;灝忎簬鍙蜂箣鍚?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;?’錛岃繘鍏?#8220;澶勭悊鎸囦護”鐘舵€併€?br />
5. 鍦?#8220;灝忎簬鍙蜂箣鍚?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;/’錛岃繘鍏?#8220;緇撴潫TAG”鐘舵€併€?br />
6. 鍦?#8220;灝忎簬鍙蜂箣鍚?#8221;鐘舵€佷笅錛岃鍏ユ湁鏁堢殑ID瀛楃錛岃繘鍏?#8220;璧峰TAG”鐘舵€併€?br />
7. 鍦?#8220;娉ㄩ噴鍓嶄竴” 鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;-’錛?榪涘叆“娉ㄩ噴鍓嶄簩” 鐘舵€併€?br />
8. 鍦?#8220;娉ㄩ噴鍓嶄簩” 鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;-’錛?榪涘叆“娉ㄩ噴” 鐘舵€併€?br />
9. 鍦?“璧峰TAG” 鐘舵€併€?#8220;緇撴潫TAG” 鐘舵€?銆?#8220;鏂囨湰” 鐘舵€併€?#8220;娉ㄩ噴”鐘舵€?鍜?#8220;澶勭悊鎸囦護”鐘舵€佺粨鏉熷悗錛岄噸鏂板洖鍒?#8220;絀?#8221;鐘舵€佷笅銆?/p>
榪欎釜鐘舵€佹満鐨勫浘褰㈣〃紺哄涓嬶細
涓嬮潰鎴戜滑鏉ョ湅鐪嬩唬鐮佸疄鐜幫細
void xml_parser_parse(XmlParser* thiz, const char* xml)
{
/*瀹氫箟鐘舵€佺殑鏋氫婦鍊?/
enum _State
{
STAT_NONE,
STAT_AFTER_LT,
STAT_START_TAG,
STAT_END_TAG,
STAT_TEXT,
STAT_PRE_COMMENT1,
STAT_PRE_COMMENT2,
STAT_COMMENT,
STAT_PROCESS_INSTRUCTION,
}state = STAT_NONE;
thiz->read_ptr = xml;
/*鎸囬拡浠庡ご縐誨姩鍒板熬*/
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
char c = thiz->read_ptr[0];
switch(state)
{
case STAT_NONE:
{
if(c == '<')
{
/*鍦?#8220;絀?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;<’錛岃繘鍏?#8220;灝忎簬鍙蜂箣鍚?#8221;鐘舵€併€?/
xml_parser_reset_buffer(thiz);
state = STAT_AFTER_LT;
}
else if(!isspace(c))
{
/*鍦?#8220;絀?#8221;鐘舵€佷笅錛岃鍏ラ潪‘<’闈炵┖鐧界殑瀛楃錛岃繘鍏?#8220;鏂囨湰”鐘舵€併€?/
state = STAT_TEXT;
}
break;
}
case STAT_AFTER_LT:
{
if(c == '?')
{
/*鍦?#8220;灝忎簬鍙蜂箣鍚?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;?’錛岃繘鍏?#8220;澶勭悊鎸囦護”鐘舵€併€?/
state = STAT_PROCESS_INSTRUCTION;
}
else if(c == '/')
{
/*鍦?#8220;灝忎簬鍙蜂箣鍚?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;/’錛岃繘鍏?#8220;緇撴潫TAG”鐘舵€併€?/
state = STAT_END_TAG;
}
else if(c == '!')
{
/*鍦?#8220;灝忎簬鍙蜂箣鍚?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;錛?#8217;錛岃繘鍏?#8220;娉ㄩ噴鍓嶄竴” 鐘舵€?/
state = STAT_PRE_COMMENT1;
}
else if(isalpha(c) || c == '_')
{
/*鍦?#8220;灝忎簬鍙蜂箣鍚?#8221;鐘舵€佷笅錛岃鍏ユ湁鏁堢殑ID瀛楃錛岃繘鍏?#8220;璧峰TAG”鐘舵€併€?/
state = STAT_START_TAG;
}
else
{
}
break;
}
case STAT_START_TAG:
{
/*榪涘叆瀛愮姸鎬?/
xml_parser_parse_start_tag(thiz);
state = STAT_NONE;
break;
}
case STAT_END_TAG:
{
/*榪涘叆瀛愮姸鎬?/
xml_parser_parse_end_tag(thiz);
state = STAT_NONE;
break;
}
case STAT_PROCESS_INSTRUCTION:
{
/*榪涘叆瀛愮姸鎬?/
xml_parser_parse_pi(thiz);
state = STAT_NONE;
break;
}
case STAT_TEXT:
{
/*榪涘叆瀛愮姸鎬?/
xml_parser_parse_text(thiz);
state = STAT_NONE;
break;
}
case STAT_PRE_COMMENT1:
{
if(c == '-')
{
/*鍦?#8220;娉ㄩ噴鍓嶄竴” 鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;-’錛?榪涘叆“娉ㄩ噴鍓嶄簩” 鐘舵€併€?/
state = STAT_PRE_COMMENT2;
}
else
{
}
break;
}
case STAT_PRE_COMMENT2:
{
if(c == '-')
{
/*鍦?#8220;娉ㄩ噴鍓嶄簩” 鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;-’錛?榪涘叆“娉ㄩ噴” 鐘舵€併€?/
state = STAT_COMMENT;
}
else
{
}
}
case STAT_COMMENT:
{
/*榪涘叆瀛愮姸鎬?/
xml_parser_parse_comment(thiz);
state = STAT_NONE;
break;
}
default:break;
}
if(*thiz->read_ptr == '\0')
{
break;
}
}
return;
}
瑙f瀽騫舵病鏈夊湪姝ょ粨鏉燂紝鍘熷洜鏄儚“璧峰TAG”鐘舵€佸拰“澶勭悊鎸囦護”鐘舵€佺瓑錛屽畠浠笉鏄師瀛愮殑錛屽唴閮ㄨ繕鍖呭惈涓€浜涘瓙鐘舵€侊紝濡俆AG鍚嶇О錛屽睘鎬у悕鍜屽睘鎬у€肩瓑錛屽畠浠渶瑕佽繘涓€姝ュ垎瑙c€傚湪鑰冭檻瀛愮姸鎬佹椂錛屾垜浠彲浠ュ繕鎺夊畠鎵€澶勭殑涓婁笅鏂囷紝鍙€冭檻瀛愮姸鎬佹湰韜紝榪欐牱闂浼氬緱鍒扮畝鍖栥€備笅闈㈢湅涓€涓嬭搗濮婽AG鐨勭姸鎬佹満銆?/p>
鍋囪鎴戜滑瑕佽В鏋愪笅闈㈣繖鏍蜂竴涓搗濮婽AG錛?br /> <mime-type xmlns=”http://www.freedesktop.org/standards/shared-mime-info” type=”all/all”>
鎴戜滑搴旇鎬庢牱鍘誨仛鍛紵榪樻槸鎸夊墠闈㈢殑鏂規硶錛岃涓€涓寚閽堟寚鍚戠紦鍐插尯鐨勫ご閮紝鐒跺悗縐誨姩鎸囬拡錛岀洿鍒版寚鍚戠紦鍐插尯鐨勫熬閮ㄣ€傚湪榪欎釜榪囩▼涓紝鎸囬拡鍙兘鎸囧悜錛孴AG鍚嶇О錛屽睘鎬у悕鍜屽睘鎬у€箋€傜敱姝ゆ垜浠彲浠ュ畾涔夊嚭鐘舵€佹満鐨勪富瑕佺姸鎬侊細
1. “TAG鍚嶇О”鐘舵€?br /> 2. “灞炴€у悕”鐘舵€?br /> 3. “灞炴€у€?#8221;鐘舵€?/p>
涓轟簡鏂逛究澶勭悊錛屽啀寮曚袱涓腑闂寸姸鎬侊紝“灞炴€у悕涔嬪墠”鐘舵€佸拰“灞炴€у€間箣鍓?#8221;鐘舵€併€?/p>
鐘舵€佽漿鎹㈠嚱鏁幫細
鍒濆鐘舵€佷負“TAG鍚嶇О”鐘舵€?br /> 1. 鍦?#8220;TAG鍚嶇О”鐘舵€佷笅錛岃鍏ョ┖鐧藉瓧絎︼紝榪涘叆“灞炴€у悕涔嬪墠”鐘舵€併€?br /> 2. 鍦?#8220;TAG鍚嶇О”鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;/’鎴?#8216;>’錛岃繘鍏?#8220;緇撴潫”鐘舵€併€?br /> 3. 鍦?#8220;灞炴€у悕涔嬪墠”鐘舵€佷笅錛岃鍏ュ叾瀹冮潪絀虹櫧瀛楃錛岃繘鍏?#8220;灞炴€у悕”鐘舵€併€?br /> 4. 鍦?#8220;灞炴€у悕”鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;=’錛岃繘鍏?#8220;灞炴€у€間箣鍓?#8221;鐘舵€併€?br /> 5. 鍦?#8220;灞炴€у€間箣鍓?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;“’錛岃繘鍏?#8220;灞炴€у€?#8221;鐘舵€併€?br /> 6. 鍦?#8220;灞炴€у€?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;”’錛屾垚鍔熻В鏋愬睘鎬у悕鍜屽睘鎬у€鹼紝鍥炲埌“灞炴€у悕涔嬪墠”鐘舵€併€?br /> 7. 鍦?#8220;灞炴€у悕涔嬪墠”鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;/’鎴?#8216;>’錛岃繘鍏?#8220;緇撴潫”鐘舵€併€?/p>
鐢變簬澶勭悊鎸囦護(PI)閲屼篃鍖呭惈浜嗗睘鎬х姸鎬侊紝涓轟簡閲嶇敤灞炴€цВ鏋愮殑鍔熻兘錛屾垜浠妸灞炴€х殑鐘舵€佸啀鎻愬彇涓轟竴涓瓙鐘舵€併€傝繖鏍鳳紝“璧峰TAG”鐘舵€佺殑鍥懼艦琛ㄧず濡備笅錛?br />
涓嬮潰鎴戜滑鐪嬩唬鐮佸疄鐜幫細
static void xml_parser_parse_attrs(XmlParser* thiz, char end_char)
{
int i = 0;
enum _State
{
STAT_PRE_KEY,
STAT_KEY,
STAT_PRE_VALUE,
STAT_VALUE,
STAT_END,
}state = STAT_PRE_KEY;
char value_end = '\"';
const char* start = thiz->read_ptr;
thiz->attrs_nr = 0;
for(; *thiz->read_ptr != '\0' && thiz->attrs_nr < MAX_ATTR_NR; thiz->read_ptr++)
{
char c = *thiz->read_ptr;
switch(state)
{
case STAT_PRE_KEY:
{
if(c == end_char || c == '>')
{
/*鍦?#8220;灞炴€у悕涔嬪墠”鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;/’鎴?#8216;>’錛岃繘鍏?#8220;緇撴潫”鐘舵€併€?/
state = STAT_END;
}
else if(!isspace(c))
{
/*鍦?#8220;灞炴€у悕涔嬪墠”鐘舵€佷笅錛岃鍏ュ叾瀹冮潪絀虹櫧瀛楃錛岃繘鍏?#8220;灞炴€у悕”鐘舵€併€?/
state = STAT_KEY;
start = thiz->read_ptr;
}
}
case STAT_KEY:
{
if(c == '=')
{
/*鍦?#8220;灞炴€у悕”鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;=’錛岃繘鍏?#8220;灞炴€у€間箣鍓?#8221;鐘舵€併€?/
thiz->attrs[thiz->attrs_nr++] = (char*)xml_parser_strdup(thiz, start, thiz->read_ptr - start);
state = STAT_PRE_VALUE;
}
break;
}
case STAT_PRE_VALUE:
{
/*鍦?#8220;灞炴€у€間箣鍓?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;“’錛岃繘鍏?#8220;灞炴€у€?#8221;鐘舵€併€?/
if(c == '\"' || c == '\'')
{
state = STAT_VALUE;
value_end = c;
start = thiz->read_ptr + 1;
}
break;
}
case STAT_VALUE:
{
/*鍦?#8220;灞炴€у€?#8221;鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;”’錛屾垚鍔熻В鏋愬睘鎬у悕鍜屽睘鎬у€鹼紝鍥炲埌“灞炴€у悕涔嬪墠”鐘舵€併€?/
if(c == value_end)
{
thiz->attrs[thiz->attrs_nr++] = (char*)xml_parser_strdup(thiz, start, thiz->read_ptr - start);
state = STAT_PRE_KEY;
}
}
default:break;
}
if(state == STAT_END)
{
break;
}
}
for(i = 0; i < thiz->attrs_nr; i++)
{
thiz->attrs[i] = thiz->buffer + (size_t)(thiz->attrs[i]);
}
thiz->attrs[thiz->attrs_nr] = NULL;
return;
}
璁板緱鍦╔ML閲岋紝鍗曞紩鍙峰拰鍙屽紩鍙烽兘鍙互鐢ㄦ潵鐣屽畾灞炴€у€鹼紝鎵€浠ヤ笂闈㈠姝ゅ仛浜嗙壒孌婂鐞嗐€?/p>
static void xml_parser_parse_start_tag(XmlParser* thiz)
{
enum _State
{
STAT_NAME,
STAT_ATTR,
STAT_END,
}state = STAT_NAME;
char* tag_name = NULL;
const char* start = thiz->read_ptr - 1;
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
char c = *thiz->read_ptr;
switch(state)
{
case STAT_NAME:
{
/*鍦?#8220;TAG鍚嶇О”鐘舵€佷笅錛岃鍏ョ┖鐧藉瓧絎︼紝灞炴€у瓙鐘舵€併€?/
/*鍦?#8220;TAG鍚嶇О”鐘舵€佷笅錛岃鍏ュ瓧絎?#8216;/’鎴?#8216;>’錛岃繘鍏?#8220;緇撴潫”鐘舵€併€?/
if(isspace(c) || c == '>' || c == '/')
{
state = (c != '>' && c != '/') ? STAT_ATTR : STAT_END;
}
break;
}
case STAT_ATTR:
{
/*榪涘叆“灞炴€?#8221;瀛愮姸鎬?/
xml_parser_parse_attrs(thiz, '/');
state = STAT_END;
break;
}
default:break;
}
if(state == STAT_END)
{
break;
}
}
for(; *thiz->read_ptr != '>' && *thiz->read_ptr != '\0'; thiz->read_ptr++);
return;
}
澶勭悊鎸囦護鐨勮В鏋愬拰璧峰TAG鐨勮В鏋愬熀鏈笂鏄竴鏍風殑錛岃繖閲屽彧鏄湅涓€涓嬩唬鐮侊細
static void xml_parser_parse_pi(XmlParser* thiz)
{
enum _State
{
STAT_NAME,
STAT_ATTR,
STAT_END
}state = STAT_NAME;
char* tag_name = NULL;
const char* start = thiz->read_ptr;
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
char c = *thiz->read_ptr;
switch(state)
{
case STAT_NAME:
{
/*鍦?#8220;TAG鍚嶇О”鐘舵€佷笅錛岃鍏ョ┖鐧藉瓧絎︼紝灞炴€у瓙鐘舵€併€?/
/*鍦?#8220;TAG鍚嶇О”鐘舵€佷笅錛?#8216;>’錛岃繘鍏?#8220;緇撴潫”鐘舵€併€?/
if(isspace(c) || c == '>')
{
state = c != '>' ? STAT_ATTR : STAT_END;
}
break;
}
case STAT_ATTR:
{
/*榪涘叆“灞炴€?#8221;瀛愮姸鎬?/
xml_parser_parse_attrs(thiz, '?');
state = STAT_END;
break;
}
default:break;
}
if(state == STAT_END)
{
break;
}
}
tag_name = thiz->buffer + (size_t)tag_name;
for(; *thiz->read_ptr != '>' && *thiz->read_ptr != '\0'; thiz->read_ptr++);
return;
}
娉ㄩ噴錛岀粨鏉烼AG鍜屾枃鏈殑瑙f瀽闈炲父綆€鍗曪紝榪欓噷緇撳悎浠g爜鐪嬬湅灝辮浜嗭細
“娉ㄩ噴”瀛愮姸鎬佺殑澶勭悊錛?/p>
static void xml_parser_parse_comment(XmlParser* thiz)
{
enum _State
{
STAT_COMMENT,
STAT_MINUS1,
STAT_MINUS2,
}state = STAT_COMMENT;
const char* start = ++thiz->read_ptr;
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
char c = *thiz->read_ptr;
switch(state)
{
case STAT_COMMENT:
{
/*鍦?#8220;娉ㄩ噴”鐘舵€佷笅錛岃鍏?#8216;-’錛岃繘鍏?#8220;鍑忓彿涓€”鐘舵€併€?/
if(c == '-')
{
state = STAT_MINUS1;
}
break;
}
case STAT_MINUS1:
{
if(c == '-')
{
/*鍦?#8220;鍑忓彿涓€”鐘舵€佷笅錛岃鍏?#8216;-’錛岃繘鍏?#8220;鍑忓彿浜?#8221;鐘舵€併€?/
state = STAT_MINUS2;
}
else
{
state = STAT_COMMENT;
}
break;
}
case STAT_MINUS2:
{
if(c == '>')
{
/*鍦?#8220;鍑忓彿浜?#8221;鐘舵€佷笅錛岃鍏?#8216;>’錛岀粨鏉熻В鏋愩€?/
return;
}
else
{
state = STAT_COMMENT;
}
}
default:break;
}
}
return;
}
“緇撴潫TAG”瀛愮姸鎬佺殑澶勭悊錛?/p>
static void xml_parser_parse_end_tag(XmlParser* thiz)
{
char* tag_name = NULL;
const char* start = thiz->read_ptr;
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
/*璇誨叆‘>’錛岀粨鏉熻В鏋愩€?/
if(*thiz->read_ptr == '>')
{
break;
}
}
return;
}
“鏂囨湰”瀛愮姸鎬佺殑澶勭悊錛?/p>
static void xml_parser_parse_text(XmlParser* thiz)
{
const char* start = thiz->read_ptr - 1;
for(; *thiz->read_ptr != '\0'; thiz->read_ptr++)
{
char c = *thiz->read_ptr;
/*璇誨叆‘>’錛岀粨鏉熻В鏋愩€?/
if(c == '<')
{
if(thiz->read_ptr > start)
{
}
thiz->read_ptr--;
return;
}
else if(c == '&')
{
/*璇誨叆‘&’錛岃繘鍏ュ疄浣?entity)瑙f瀽瀛愮姸鎬併€?/
xml_parser_parse_entity(thiz);
}
}
return;
}
瀹炰綋(entity)瀛愮姸鎬佹瘮杈冪畝鍗曪紝榪欓噷涓嶅仛榪涗竴姝ュ垎鏋愪簡錛岀暀緇欒鑰呭仛緇冧範鍚?/p>
杞嚜:http://carllgc.blog.ccidnet.com/blog-htm-do-showone-uid-4092-type-blog-itemid-263093.html
浣滀負涓€浣?span>Java紼嬪簭鍛橈紝濡傛灉鎮ㄦ病鏈夋帴瑙﹁繃寮€婧愯蔣浠躲€侀」鐩垨妗嗘灦鐨勮瘽錛屾亹鎬曟湁浜涗笉鍙€濊銆傝槳杞扮儓鐑堢殑寮€婧愯繍鍔ㄨ搗婧愪簬Linux鎿嶄綔緋葷粺錛?/span>Apache鍩洪噾浼氬湪鍏朵腑鎵紨浜嗕腑嫻佺牓鏌辯殑瑙掕壊錛屼笟鐣屽法鎿?/span>SUN錛?/span>IBM錛?/span> BEA 鍜?/span>Oracle絳夊叕鍙哥殑縐瀬鍙備笌錛屼嬌寰楀0鍔挎旦澶х殑寮€婧愯繍鍔ㄦ垚涓鴻蔣浠跺紑鍙戦鍩熷娍涓嶅彲鎸$殑鍔涢噺銆?/span>2001騫?/span>11鏈堬紝IBM鍚?/span>Apache鍩洪噾浼氭崘鐚嚭Visual Age for Java錛岃繖涓湅浼肩┓閫旀湯璺殑浜у搧緇忎紬澶氶珮鎵嬬殑鏀歸€狅紝婕斿彉涓鴻緣鐓屼竴鏃剁殑Eclipse錛岀洿鎺ュ嚮璐ヤ簡涓嶅紑婧愮殑JBuilder錛岃鍋氱紪璇戝櫒璧峰鐨?/span>Borland鍏徃鍑犱箮鍏沖紶澶у悏銆?/span>Eclipse榪欎釜浜у搧濡傛緇忓吀錛屼互鑷充簬寰蔣鐨?/span>Visual Studio閮藉緱鍚戝畠瀛︿範銆傚湪Apache Harmony鐨勫洿榪藉牭鎴笅錛?/span>Java鐨勫彂鏄庤€?/span>Sun鍏徃涓€鐪嬪娍澶翠笉濡欙紝浜?/span>2006騫村甯?/span>Java寮€婧愶紝闅忓悗鍙堝叕寮€浜嗗叾鏃楄埌綰т駭鍝?/span>Solaris鐨勬簮浠g爜銆備粖騫?/span>1鏈堬紝寮€婧愮殑姝誨澶淬€佸喎閰瘋嚜縐佺殑寰蔣涔熶笉寰椾笉鍦?/span>MS-RL鍗忚涓嬪叕寮€.Net鐨勬簮浠g爜銆備絾鏄紝鍦ㄨ繖濡傜伀濡傝嵓鐨勫紑婧愯繍鍔ㄤ腑錛屾垜浠腑鍥界殑紼嬪簭鍛樺張鏈夊灝戣礎鐚憿錛屾垜浠紑鍒涗簡鍝簺妗嗘灦銆侀」鐩拰浜у搧錛屼負寮€婧愮晫娣葷爾鍔犵摝鍛紵浠ョ瑪鑰呯煭嫻呯殑鐩厜鐪嬫潵錛屾垜浠寮€婧愮晫璐$尞鐨勪笢瑗挎亹鎬曞緢灝戯紝鑳藉涓庡浗澶栫粡鍏稿紑婧愰」鐩竴杈冮珮涓嬬殑錛屽皯涔嬪張灝戠煟錛?/span>
浣滀負涓€鍚嶄腑鍥界殑紼嬪簭鍛橈紝鍜變滑鑳芥病鏈夐仐鎲懼悧錛熶負浠€涔堢粡鍏哥殑Apache Web Server涓嶆槸涓浗浜哄啓鐨勶紱涓轟粈涔?/span>Linus Torvalds鍦ㄥぇ瀛︽椂浠e氨鍐欏嚭Linux騫舵尟鑷備竴鍛鹼紝搴旇€呬簯闆嗭紱涓轟粈涔?/span>JBoss鑳戒笌宸ㄦ棤闇稿紡鐨?/span>Websphere鐩告姉琛★紱涓轟粈涔?/span>MySQL鑳藉湪Oracle鍜?/span>SQL Server鐨勫す鍑諱笅鍙戝睍騫跺.澶?/span>…… 錛熷姝ょ瓑絳夐棶棰橈紝鍦ㄩ仐鎲句箣浣欙紝鎴戞兂鎴戜滑搴旇鑺辯偣鏃墮棿濂藉ソ鎬濊€冧竴涓嬶紝涓浗鐨勮蔣浠朵駭涓氭€庝箞浜嗭紝涓浗鐨勭▼搴忓憳鍙堟€庝箞鍟︼紵
鍦ㄧ瑪鑰呯湅鏉ワ紝鎴戜滑鐨勭▼搴忓憳瀵瑰紑婧愮殑鐞嗚В鏄浉褰撶嫮闅樼殑銆傚浗瀛﹀ぇ甯堢帇鍥界淮鏇捐榪囷紝鍙ゅ線浠婃潵鎴愬ぇ瀛﹂棶澶т簨涓氳€呰緇忓巻涓夌澧冪晫錛?#8220;鏄ㄥ瑗塊鍑嬬ⅶ鏍戯紝鐙笂楂樻ゼ錛屾湜灝藉ぉ娑礬”錛岃繖鏄涓€閲嶅鐣岋紝榪鋒儤涔燂紱“琛e甫娓愬緇堜笉鎮旓紝涓轟紛娑堝緱浜烘啍鎮?#8221;錛岃嫤鑻︽眰绱箣澧冪晫涔燂紱絎笁閲嶅鐣屼負“浼楅噷瀵諱粬鍗冪櫨搴︼紝钃︾劧鍥為錛岄偅浜哄嵈鍦ㄧ伅鐏槕鐝婂”錛岀粡鍘嗗灝戞鐨勫け璐ュ拰鎸姌鍚庯紝緇堜簬鍙傞€忕湡璋涳紝棰嗘偀鐪熺悊銆傛垜瑙夊緱寮€婧愪篃鏈変笁閲嶅鐣岋細
棣栧厛錛屾垜浠鏁炲紑蹇冭兏錛屾嫢鎶卞紑婧愶紙Open
to Open
Source)銆傝繖閲嶅鐣屾垜浠ぇ瀹墮兘鑳藉仛鍒幫紝鎷挎潵涓諱箟鍢涳紝璋佷漢涓嶄細銆傚綋鎴戜滑鐨勯」鐩渶瑕佹暟鎹簱鏃訛紝灝卞幓涓嬭澆涓€涓厤璐筂ySQL錛涢渶瑕両DE鏃訛紝鍘諱笅杞?
Eclipse錛涢渶瑕佺増鏈帶鍒跺伐鍏鋒椂錛屽氨鍘諱笅杞紺VS錛涢渶瑕佸啓鎼滅儲寮曟搸鏃訛紝Lucene鍙兘鏄垜浠殑鏈€鐖憋紱褰撴垜浠紑鍙慗2EE
Web搴旂敤鏃訛紝Struts/JSF鍔燞ibernate/iBATIS鍐嶅姞涓奡pring鎴栬鎴愪負鎴戜滑鐨勯閫夋灦鏋勩€備絾鏄紝鎴戜滑緇濆ぇ閮ㄥ垎紼嬪簭鍛橀兘鍋滅暀鍦ㄨ繖
涓眰嬈′笂錛屽ぇ瀹朵笅杞戒箣鍚庯紝鐪嬬湅鏂囨。浠嬬粛錛屽畨瑁呫€侀厤緗茍鑳借繍琛岋紝灝變互涓轟竾浜嬪ぇ鍚夛紝涓€鍒囬『鍒┿€傚伓灝旈亣鍒頒竴浜涢棶棰橈紝鍘籊oogle涓€鎼滐紝絳旀绔嬮┈鍙緱銆?
鍏舵錛屾垜浠娣卞叆寮€婧愶紝浜嗚В寮€婧愶紙Dig
into Open
Source)銆傝杈懼埌榪欎釜灞傛錛屽氨鏈変簺闅懼害浜嗐€傛垜浠笉浣嗚鐭ュ叾鐒訛紝榪樿鐭ュ叾鎵€浠ョ劧銆?#8220;鐭ュ叾鎵€浠ョ劧”鐨勬渶濂藉姙娉曞氨鏄笅杞芥簮浠g爜錛屼粩緇嗙爺璇伙紝鎻f懇騫墮浼氭簮浠?
鐮佺殑綺句箟錛岀湅鐪嬭繖浜涚粡榪囪澶氶珮鎵嬩慨鏀圭殑婧愪唬鐮佺┒绔熻棌鏈変粈涔堢巹鏈猴紝鎴戜滑鑳戒粠鍏朵腑瀛︿範鍒板摢浜涜璁℃€濇兂鍙婅璁℃ā寮忥紝鑳藉鐢ㄥ叾涓摢浜涙簮浠g爜錛屼漢瀹惰繍鐢ㄤ簡鍝簺杞歡綆?
鐞嗘€濇兂鎶婅繖浜涙潵鑷笘鐣屽悇鍦扮▼搴忓憳鐨勫姵鍔ㄦ眹闆嗘垚涓€涓駭鍝侊紝浠g爜鏋舵瀯濡備綍錛岃蔣浠墮厤緗鐞嗗張鏄€庢牱榪涜鐨?#8230;…錛岀瓑絳夌瓑絳夛紝鎴戜滑浠庢簮浠g爜涓涔犵殑涓滆タ澶浜嗐€傚湪闃?
璇繪簮浠g爜鏃訛紝鎴戜滑瑕佸闂嚜宸卞嚑涓負浠€涔堬紝榪欐牱灝變細鏀惰幏鏇村銆?
鍐嶆錛屾垜浠铻嶅叆寮€婧愶紝璐$尞寮€婧愶紙Get
involved in Open
Source)銆傚綋鎴戜滑褰誨簳鐞嗚В璇ラ」鐩簮浠g爜鍚庯紝鎴戜滑搴斿彂鎸ヤ竴涓?#8220;浜轟漢涓烘垜錛屾垜涓轟漢浜?#8221;鐨勬€濇兂錛屾垨緇撳悎鎮ㄧ殑瀹為檯闇€瑕侊紝鎴栫粨鍚堟偍鐨勬柊鎯蟲硶錛屾垨閽堝Mail
lists涓婄殑闂錛屽璇ュ紑婧愰」鐩姞浠ユ敼榪涘拰鍒涙柊錛屽茍鎶婅嚜宸辯殑浠g爜璐$尞鍑烘潵錛岃澶у璇勪及銆傚綋鐒訛紝濡傛灉鎮ㄦ湁濂界殑鎯蟲硶錛屾偍瀹屽叏鍙互鍒涘緩鑷繁鐨勫紑婧愰」
鐩紝Apache鍩洪噾浼氫腑浼楀鐨勫紑婧愰」鐩笉閮芥槸鎴戜滑騫垮ぇ紼嬪簭鍛樹竴鎵嬪垱寤虹殑鍚楋紵浣嗘槸錛屽湪鍒涘緩鏂板紑婧愰」鐩椂錛屽垏蹇屼笉瑕侀噸鏂板彂鏄庤疆瀛愩€?
絎旇€呮墠鐤忓嫻咃紝鎯充互Apache Jakarta欏圭洰鍖呬腑鐨勬牳蹇冮」鐩甌omcat涓轟緥錛屽笇鏈涢€氳繃闃呰婧愮爜錛岃兘浠庤繖涓粡鍏擱」鐩腑瀛﹀埌鏇村鐨勪笢瑗匡紝涓烘垜浠腑鍥界殑寮€婧愪簨涓氳搗鍒版姏鐮栧紩鐜夌殑浣滅敤銆?
涓嬮潰鎴戜滑灝卞紑濮嬫垜浠殑Tomcat婧愮爜瀛︿範涔嬫梾銆?
1. 涓嬭澆Tomcat6.0鐨勬簮浠g爜
棣栧厛錛屾垜浠緱涓嬭澆Tomcat6.0鐨勬簮浠g爜銆俆omcat婧愪唬鐮佺殑鐗堟湰鎺у埗宸ュ叿涓嶆槸CVS錛岃€屾槸Subversion錛屽鏋滄偍鐨勬満鍣ㄤ笂娌℃湁瀹夎Subversion錛岃浠?/span> http://subversion.tigris.org/servlets/ProjectDocumentList?folderID=91 涓嬭澆騫跺畨瑁呰繖涓紑婧愮殑鐗堟湰鎺у埗宸ュ叿銆傚綋鐒訛紝濡傛灉鎮ㄦ兂浠?/span>Eclipse涓洿鎺ュ鍏?/span>Tomcat婧愪唬鐮侊紝璇蜂粠http://subclipse.tigris.org/update_1.0.x涓嬭澆Subversion鎻掍歡錛屽嵆鍙鍏?/span>Tomcat婧愪唬鐮併€傚畨瑁呭畬鎴愬悗錛岃鍦?/span>MS-DOS紿楀彛涓敭鍏?/span>svn export help錛屾偍灝嗕細鐪嬪埌錛?/span>
C:\Documents and Settings\carlwu>svn help export
export: 浜х敓涓€涓棤鐗堟湰鎺у埗鐨勭洰褰曟爲鍓湰銆?/span>
鐢ㄦ硶: 1銆?/span>export [-r REV] URL[@PEGREV] [PATH]
2銆?/span>export [-r REV] PATH1[@PEGREV] [PATH2]
1銆佷粠 URL 鎸囧畾鐨勪粨搴擄紝瀵煎嚭涓€涓共鍑€鐨勭洰褰曟爲鍒?/span> PATH銆傚鏋滄湁鎸囧畾
REV 鐨勮瘽錛屽唴瀹瑰嵆涓鴻鐗堟湰鐨勶紝鍚﹀垯灝辨槸 HEAD 鐗堟湰銆傚鏋?/span> PATH
琚渷鐣ョ殑璇濓紝URL鐨勬渶鍚庨儴浠戒細琚敤鏉ュ綋鎴愭湰鍦扮殑鐩綍鍚嶇О銆?/span>
2銆佸湪宸ヤ綔鍓湰涓紝浠庢寚瀹氱殑 PATH1 瀵煎嚭涓€涓共鍑€鐨勭洰褰曟爲鍒?/span> PATH2銆傚鏋?/span>
鏈夋寚瀹?/span> REV 鐨勮瘽錛屼細浠庢寚瀹氱殑鐗堟湰瀵煎嚭錛屽惁鍒欎粠宸ヤ綔鍓湰瀵煎嚭銆傚鏋?/span>
PATH2 琚渷鐣ョ殑璇濓紝PATH1 鐨勬渶鍚庨儴浠戒細琚敤鏉ュ綋鎴愭湰鍦扮殑鐩綍鍚嶇О銆?/span>
濡傛灉娌℃湁鎸囧畾 REV 鐨勮瘽錛屾墍鏈夌殑鏈湴淇敼閮戒繚鐣欙紝浣嗘槸鏈撼鍏ョ増鏈帶鍒?/span>
鐨勬枃浠朵笉浼氳澶嶅埗銆?/span>
濡傛灉鎸囧畾浜?/span> PEGREV 錛屽皢浠庢寚瀹氱殑鐗堟湰鏈紑濮嬫煡鎵俱€?/span>
鏈夋晥閫夐」:銆傘€傘€傘€傘€傘€?/span>
鎴戜滑鐪嬪埌Subversion緇欐垜浠彁渚涗簡闈炲父鍙嬪ソ鐨勫府鍔╋紝騫朵笖鏄腑鏂囩殑錛岀湅鏉ヤ腑鍥界▼搴忓憳瀵硅繖涓紑婧愰」鐩湁鎵€璐$尞銆傛帴涓嬫潵錛岃鍦?/span>MS-DOS涓嬮敭鍏ワ細
svn export http://svn.apache.org/repos/asf/tomcat/tc6.0.x/tags/TOMCAT_6_0_0/ D:\carl_wu\tomcat\src\
榪欎釜鍛戒護鐨勬剰鎬濇槸鎶?/span>Tomcat6.0鐨勬簮浠g爜浠?/span>Subversion搴撲腑瀵煎叆鍒版湰鏈虹殑D:\carl_wu\tomcat\src\鐩綍錛屽懡浠よ繍琛屽悗錛屾偍紼嶇瓑鍑犲垎閽燂紝灝變細鐪嬪埌Tomcat鐨勬簮浠g爜欏哄埄瀵煎叆鍒扮洰鏍囩洰褰曘€備笅闈㈡槸婧愪唬鐮佺殑鐩綍鏈烘瀯錛屼粠榪欎釜鐩綍緇撴瀯涓紝鎴戜滑鍙互鐪嬪嚭璇ラ」鐩殑寮€鍙戣€呬嬌鐢ㄧ殑IDE鏄?/span>Eclipse錛屽洜涓烘垜浠湅鍒頒簡鐔熸倝鐨?/span>.project鍙?/span>.classpath鏂囦歡銆傚鏋滄偍鎵撶畻寮€鍙戜竴涓?/span>Stand alone鐨?/span>Java搴旂敤紼嬪簭錛屼笉濡ㄥ€熼壌涓€涓?/span>Tomcat鐨勭洰褰曠粨鏋勶紝鎶婅剼鏈枃浠舵斁鍦?/span>bin鐩綍錛屽皢xml鍜?/span>properties閰嶇疆鏂囦歡鏀懼湪conf鐩綍涓紝鎶?/span>Java婧愮爜鏂囦歡鏀懼湪java鎴栬€?/span>src鐩綍涓紝璧勬簮鏂囦歡姣斿璇村浘鐗囨枃浠訛紝ini鏂囦歡鍙婂叾瀹冪殑涓€浜涢潤鎬佽祫婧愭枃浠跺彲浠ユ斁鍦?/span>res鐩綍錛屾祴璇曟簮浠g爜鍙互鏀懼湪test鐩綍涓€傝繖鏄竴涓吀鍨嬬殑Java搴旂敤紼嬪簭鐨勭洰褰曟満鏋勶紝絎旇€呬互鍓嶆浘鎺ヨЕ鍒頒竴涓潵鑷編鍥界殑浜у搧錛屽叾婧愪唬鐮佺洰褰曠粨鏋勫拰Tomcat鍙婂叾鐩稿儚銆?/span>
2. 緙栬瘧騫惰繍琛?/span>
浠g爜涓嬭澆鍚庯紝鎴戜滑鎺ヤ笅鏉ュ氨鏄緙栬瘧騫惰繍琛?/span>Tomcat銆備竴鎻愮紪璇戯紝鎴戜滑涓嶇浼氭兂鍒板彲鐖辯殑Ant銆備笉閿欙紝Tomcat姝f槸浠?/span>Ant浣滀負緙栬瘧宸ュ叿錛屽鏋滄偍榪樻病鏈夊畨瑁咃紝璇蜂粠http://ant.apache.org/bindownload.cgi 澶勪笅杞藉茍瀹夎瀹冦€傜劧鍚庯紝璇蜂粠Tomcat鐨勬簮浠g爜鏂囦歡鎵懼埌build.properties.default鏂囦歡錛屽茍灝嗚鏂囦歡澶嶅埗鍒?/span>build.properties錛岀劧鍚庢墦寮€build.properties錛屾壘鍒頒笅闈㈣繖琛岋細
base.path=/usr/share/java
灝嗗畠鏀逛負錛?/span>
base.path= D:/carl_wu/tomcat/share
鍦?/span>Tomcat緙栬瘧榪囩▼涓紝Ant浼氳鎴戜滑涓嬭澆涓€浜涘繀瑕佺殑渚濊禆欏圭洰錛?/span>base.path鐩綍灝辨槸鐢ㄦ潵淇濆瓨榪欎簺欏圭洰鏂囦歡鐨勶紝鎴戜滑鍙互灝嗚繖涓睘鎬ф寚鍚戜竴涓凡緇忓瓨鍦ㄧ殑鐩綍銆備慨鏀瑰畬base.path鍚庯紝鎴戜滑鍥炲埌MS-DOS紿楀彛錛屽垏鎹㈠埌Tomcat婧愪唬鐮佹墍鍦ㄧ洰褰曪紝鐒跺悗榪愯ant download鍛戒護錛屽涓嬪浘鎵€紺猴細
涓€鍒嗛挓鏈埌錛?/span>Ant灝卞憡璇夋垜浠竴涓敊璇茍鎻愮ず鎴戜滑緙栬瘧澶辮觸錛屽叿浣撻敊璇俊鎭涓嬶細
downloadzip:
[get] Getting: http://sunsite.informatik.rwth-aachen.de/eclipse/downloads/drops/R-3.2-200606291905/eclipse-JDT-3.2.zip
[get] To: D:\carl_wu\tomcat\share\file.zip
[get] Error opening connection java.io.FileNotFoundException: http://sunsite.informatik.rwth-aachen.de:3080/eclipse/downloads/drops/R-3.2-200606291905/eclipse-JDT-3.2.zip
[get] Error opening connection java.io.FileNotFoundException: http://sunsite.informatik.rwth-aachen.de:3080/eclipse/downloads/drops/R-3.2-200606291905/eclipse-JDT-3.2.zip
[get] Error opening connection java.io.FileNotFoundException: http://sunsite.informatik.rwth-aachen.de:3080/eclipse/downloads/drops/R-3.2-200606291905/eclipse-JDT-3.2.zip
[get] Can't get http://sunsite.informatik.rwth-aachen.de/eclipse/downloads/drops/R-3.2-200606291905/eclipse-JDT-3.2.zip to D:\carl_wu\tomcat\share\file.zip
BUILD FAILED
D:\carl_wu\tomcat\src\build.xml:554: The following error occurred while executing this line:
D:\carl_wu\tomcat\src\build.xml:514: Can't get http://sunsite.informatik.rwth-aachen.de/eclipse/downloads/drops/R-3.2-200606291905/eclipse-JDT-3.2.zip to D:\carl_wu\tomcat\share\file.zip
Total time: 41 seconds
榪欎釜緙栬瘧閿欒闈炲父綆€鍗曪紝灝辨槸鎵句笉鍒?/span>http://sunsite.informatik.rwth-aachen.de/eclipse/downloads/drops/R-3.2-200606291905/eclipse-JDT-3.2.zip 鏂囦歡銆傛湁浜哄彲鑳戒細鎯籌紝Tomcat鐨勭紪璇戝拰Eclipse鐨?/span>JDT鏈変粈涔堝叧緋伙紵鍏跺疄涓嶇劧錛?/span>Tomcat鏄湪Eclipse涓嬪紑鍙戠殑錛屾墍浠ラ渶瑕?/span>Eclipse鐨?/span>JDT錛?/span>Java Development tooling錛夋彃浠舵潵緙栬瘧Tomat婧愪唬鐮併€傛棦鐒舵壘涓嶅埌錛屾垜浠彧濂借嚜宸卞姩鎵嬶紝涓?/span>Google涓€鎼滐紝椹笂鍙戠幇榪欎釜鏂囦歡鐨勬湁鏁堜笅杞藉湴鍧€涓猴細http://mirror.calvin.edu/eclipse/downloads/drops/R-3.2-200606291905/eclipse-JDT-3.2.zip銆傛垜浠?/span>鎵撳紑鍒氭墠鐨?/span>build.properties鏂囦歡錛屽皢鍏?/span>34琛屼慨鏀逛負錛?/span>
jdt.loc= http://mirror.calvin.edu/eclipse/downloads/drops/R-3.2-200606291905/eclipse-JDT-3.2.zip
淇敼淇濆瓨build.properties鏂囦歡鍚庯紝閲嶆柊寮€濮?/span>ant download浠誨姟銆傝繖嬈℃垜浠瓑鐨勬椂闂磋緝闀匡紝鍥犱負eclipse-JDT-3.2.zip澶х害鏈?/span>19M錛屼笅杞介渶瑕佷竴孌墊椂闂淬€傛垜浠彲涔樻鏈轟細鍘繪場鏉尪寮勭偣鍜栧暋浠€涔堢殑錛岀瓑鎴戜滑鍝佽尪鍥炴潵錛屽彂鐜版暚涓氱殑铓傝殎Ant鍛婅瘔鎴戜滑緙栬瘧鎴愬姛錛岃櫧鐒剁紪璇戝櫒緇欏嚭鍑犱釜璀﹀憡銆傝繖鏃舵垜浠彲鍙戠幇鍒氭墠鍒涘緩鐨?/span>base.path鐩綍錛?/span>D:\carl_wu\tomcat\share錛変腑宸茬粡涓嬭澆浜?/span>6涓緷璧栭」鐩紝瀹冧滑閮芥槸Tomcat緙栬瘧鎵€蹇呴』鐨勩€?/span>
涓嬮潰灝卞紑濮嬬湡姝g殑緙栬瘧浠誨姟浜嗭紝璇峰湪MS-DOS紿楀彛鍐呴敭鍏?/span>ant騫跺洖杞︼紝Ant灝嗗湪2鍒嗛挓鍐呯紪璇?/span>1000澶氫釜婧愭枃浠跺茍灝?/span>Tomcat閮ㄧ講鍒?/span>output鐩綍銆傜紪璇戦『鍒╁畬鎴愬悗錛岃鎵撳紑Tomcat鐨勬簮浠g爜鐩綍錛屼細鍙戠幇澶氫簡涓€涓?/span>output鐩綍錛岃繖鏄?/span>Ant鐨勭紪璇戝悗鐨勮緭鍑虹洰褰曘€傝鎵撳紑Tomcat婧愪唬鐮佺殑output\build\bin瀛愮洰褰曪紝鍙屽嚮startup.bat鏂囦歡錛屾垜浠嵆鍙垚鍔熷惎鍔?/span>Tomcat6.0錛屾鏃舵垜浠殑緙栬瘧宸ヤ綔灝辯畻欏哄埄瀹屾垚浜嗐€?/span>
3. 瀵煎叆婧愪唬鐮佸埌Eclipse
3.1 璇鋒墦寮€Eclipse錛屾柊寤轟竴涓?/span>Java欏圭洰錛岀劧鍚庣偣鍑?#8220;Next”鎸夐挳錛岃閫夋嫨“Create project from existing source”錛?/span> 騫跺湪Directory鏂囨湰妗嗗唴濉叆鎴戜滑鍒氭墠涓嬭澆鐨?/span>Tomcat婧愪唬鐮佺洰褰曪紙i.e. D:\carl_wu\tomcat\src)錛岀劧鍚庣偣鍑?#8220;Next”鐩磋嚦緇撴潫銆?/span>
3.2 鎴戜滑灝嗕細鐪嬪埌Eclipse鎷掔粷緙栬瘧錛岃繖鏄洜涓?/span>Eclipse鎵句笉鍒拌欏圭洰鎸囧畾鐨勫簱鏂囦歡銆傝鍙沖嚮璇ラ」鐩紝鍦ㄥ脊鍑鴻彍鍗曚腑閫夋嫨“Properties”à“Libraries”錛岀劧鍚庡垹闄や袱涓互TOMCAT_LIBS寮€澶寸殑涓や釜搴撴枃浠訛紝鍙繚鐣欎竴涓?/span>JRE搴撴枃浠訛紝鐒跺悗鐐瑰嚮“OK”鎸夐挳錛岃繖鏃?/span>Eclipse寮€濮嬬紪璇?/span>Tomcat婧愪唬鐮侊紝浣嗘槸鍙戠幇涓€鍫嗛敊璇紝榪欐槸鍥犱負鎴戜滑娌℃湁涓鴻欏圭洰娣誨姞緙栬瘧鎵€蹇呴』鐨?/span>Jar鍖呫€?/span>
3.3 鍑嗗濂?/span>Tomcat欏圭洰鎵€蹇呴』鐨?/span>jar鏂囦歡錛屽叾瀹烇紝鍒氭墠鎴戜滑榪愯ant download浠誨姟鏃訛紝宸茬粡涓嬭澆榪囪繖浜?/span>jar鏂囦歡鍖呫€?/span>
ant.jar 錛堣鍦?/span>ant瀹夎鐩綍鐨?/span>lib瀛愮洰褰曚腑鎷瘋礉錛?/span>
commons-collections-3.1.jar 錛堜粠鍒氭墠Ant涓嬭澆鐨?/span>commons-collections-3.1瀛愮洰褰曚腑鎷瘋礉錛?/span>
commons-dbcp-1.2.1.jar錛堜粠鍒氭墠Ant涓嬭澆鐨?/span>commons-dbcp-1.2.1瀛愮洰褰曚腑鎷瘋礉錛?/span>
commons-logging-1.1.jar錛堝鏋滄偍鏈満娌℃湁榪欎釜jar鍖咃紝璇蜂粠http://commons.apache.org/downloads/download_logging.cgi澶勪笅杞斤級
commons-pool-1.2.jar錛堜粠鍒氭墠Ant涓嬭澆鐨?/span>commons-pool-1.2瀛愮洰褰曚腑鎷瘋礉錛?/span>
org.eclipse.jdt.core_3.2.0.v_671.jar錛堜粠鍒氭墠Ant涓嬭澆鐨?/span>eclipse\plugins瀛愮洰褰曚腑鎷瘋礉錛?/span>
3.4 褰撴垜浠噯澶囧ソ榪欎簺jar鏂囦歡鍚庯紝灝嗚繖浜涙枃浠舵嫹璐濆埌鏌愪竴鐩綍錛堟瘮濡傝D:\carl_wu\tomcat\tomcat_lib鐩綍錛夛紝鐒跺悗鍦?/span>Eclipse涓柊寤轟竴涓?/span>User Libraries錛屾垜浠皢榪欎釜鏂板緩鐨?/span>User Libraries鍛藉悕涓?/span>TOMCAT_LIBS錛屽茍鎶婅繖浜涙枃浠跺姞鍒?/span>TOMCAT_LIBS銆傜劧鍚庡皢鎴戜滑鏂板緩鐨?/span>TOMCAT_LIBS娣誨姞鍒?/span>Tomcat6欏圭洰銆傚彟澶栵紝鍒繕浜嗘妸JUnit搴撲篃鍔犲埌Tomcat6欏圭洰銆傝繖鏃?/span>Eclipse寮€濮嬮噸鏂扮紪璇戯紝緙栬瘧榪囩▼欏哄埄閫氳繃錛屾墍鏈夐敊璇潎娑堝け錛屾鏃?/span>Tomcat6欏圭洰鐨勭洰褰曠粨鏋勫涓嬶細
榪樻湁錛岃鎶?/span>test鐩綍涔熷姞鍏ュ埌婧愪唬鐮佷腑錛屾柟娉曟槸鍦?/span>Eclipse涓彸鍑?/span>”test”鐩綍錛岀劧鍚庡湪寮瑰嚭鑿滃崟涓€夋嫨“Build path”à”Use as Source Folder”錛屼箣鍚庢垜浠細鐪嬪埌test鐩綍涓婂氨澶氫簡涓簮浠g爜鐨勭鍙鳳紝濡備笂鍥炬墍紺恒€?/span>
3.5鍦?/span>Eclipse涓繍琛?/span>Tomcat銆傝鎵懼埌Tomcat鐨勫惎鍔ㄤ富綾?/span>org.apache.catalina.startup.Bootstrap錛屽彸鍑昏繖涓被錛屽湪寮瑰嚭鑿滃崟涓€夋嫨“Run As…”à”Open Run Dialog…”錛岀劧鍚庡湪寮瑰嚭鐨?#8220;Run”紿楀彛涓~鍏ョ▼搴忚繍琛屽弬鏁?#8220;start”鍜?/span>JVM榪愯鍙傛暟catalina.home錛屽涓嬮潰紿楀彛鎵€紺猴細
鐒跺悗鐐瑰嚮“Run”鎸夐挳錛屾垜浠皢浼氱湅鍒?/span>Tomcat姝e父鍚姩銆傛伃鍠滐紝鍜變滑鐨?/span>Tomcat婧愮爜宸茬粡鎴愬姛瀵煎叆Eclipse錛岃繖鏃訛紝鍙鍖栫殑UML鍒嗘瀽宸ュ叿鍙?/span>Debug宸ュ叿灝辮兘媧句笂鐢ㄥ満浜嗐€?/span>
3.5 璋冭瘯Tomcat錛岃鎵撳紑org.apache.jasper.compiler.Compiler綾葷殑婧愪唬鐮侊紝鍦?/span>generateJava()鏂規硶鐨勭涓€琛屾墦涓€涓柇鐐癸紝鐒跺悗鍦?/span>Eclipse鐨勮皟璇曠姸鎬佷笅榪愯Tomcat錛岀瓑Tomcat榪愯鍚庯紝鎵撳紑鎴戜滑鐨勬祻瑙堝櫒錛屽湪鍦板潃鏍忎腑杈撳叆http://localhost:8080/examples/jsp/jsp2/el/basic-comparisons.jsp騫跺洖杞︼紝鐒跺悗鎴戜滑鍙瀵熷埌Eclipse姝ゆ椂鍒囨崲鑷寵皟璇曡鍥撅細
涓婇潰鐨勫皬瀹為獙琛ㄦ槑鎴戜滑鍙互鍦?/span>Eclipse涓€氳繃Debugger瑙傚療Tomcat鐨勫唴閮ㄨ繍琛屾満鐞嗐€傚彟澶栬ˉ鍏呬竴鐐癸紝涓婇潰鐨?/span>generateJava鏂規硶鏄皢jsp鍔ㄦ€佺紪璇戣嚦java class錛岃繖涓柟娉曞彧鏄湪絎竴嬈¤姹傛垨鑰?/span>Jsp婧愮爜鍙戠敓鍙樺寲鏃舵墽琛岋紝濡傛灉鎮ㄥ啀嬈″湪嫻忚鍣ㄤ腑鍙戦€佸悓鏍風殑璇鋒眰錛屾偍灝嗙湅涓嶅埌涓婂浘鐨?/span>Debug鐣岄潰錛屽洜涓鴻鏂規硶涓嶅啀鎵ц銆?/span>
鍙﹀錛岃繕鏈変竴鐐瑰緢鏈夋剰鎬濄€?/span>Tomcat6浠ュ墠鐗堟湰鐨勬簮浠g爜鍒嗘暎鍦ㄥソ鍑犱釜瀛愰」鐩腑錛屼粬浠垎鍒彨鍋?/span>jakarta-servletapi-5錛?/span>jakarta-tomcat-5錛?/span>jakarta-tomcat-catalina錛?/span>jakarta-tomcat-connectors鍜?/span>jakarta-tomcat-jasper錛屾垜瑙夊緱Tomcat鐨勫紑鍙戣€呭彲鑳藉珜榪欐牱鍋氬お楹葷儲浜嗭紝鎵€浠?/span>Tomcat6鐗堟湰涓皢榪欎簺瀛愰」鐩兘鍚堝茍鍦ㄤ竴璧蜂簡銆備絾鏄紝榪欑鍋氭硶涓嶅埄浜庢垜浠槄璇葷悊瑙f簮浠g爜