郝 偉
XML(Extensible Markup Language)即可擴展標記語言,它與HTML一樣,都是SGML(Standard Generalized Markup Language,標準通用標記語言),即使用標記對內(nèi)容進行區(qū)分。由于Xml是Internet環(huán)境中跨平臺的,依賴于內(nèi)容的技術(shù),是當前處理結(jié)構(gòu)化文檔信息的有力工具[1]。
由于XML使用了大量的標記符,所以使用XML會占用更多的空間,但由于XML極其簡單易于掌握和使用,加上現(xiàn)在硬件技術(shù)和軟件水平的不斷發(fā)揮,所以XML已經(jīng)廣泛應(yīng)用于數(shù)據(jù)庫技術(shù)和網(wǎng)絡(luò)傳輸中[2]。
圖形和圖片在Internet中,是最常見到的文件格式,圖片都是使用二進制進行存儲,所以如果在基于文本的XML文件中傳輸?shù)脑?,就很可能是破壞XML的內(nèi)容。如,在二進制數(shù)據(jù)中,如果正好包含 “<>”這樣的標記,原XML文件的內(nèi)容就很可能會被破壞,接收端就無法正確的解析XML數(shù)據(jù),從而造成數(shù)據(jù)傳輸?shù)氖?,所以一般圖片都是與文本分開傳輸?shù)摹H欢鴶?shù)據(jù)分開傳輸雖然能解決問題,但是傳輸?shù)慕y(tǒng)一性就會被破壞,而且存儲也需要在不同的空間完成,對于一些有一定安全性要求的場合就會不太適用。
筆者在之前的文章中已經(jīng)提出了一種算法《一種基于XML的圖像存儲方法》,已經(jīng)初步解決了這個問題,但是所使用的方法沒有充分考慮效率,平均每一個碼元會增加大量的冗余數(shù)據(jù),所以當前的問題是進一步提高轉(zhuǎn)換效率,從而適應(yīng)提高傳輸效率。
現(xiàn)在各類壓縮和加密算法很多,但是全都是基于二進制的,即都是取字節(jié)0-255的所有段來進行的,這些段時,除了包括數(shù)字,大小寫字母,標點符號這些可見元素,還包括一些非可見的控件符,如回車,退格,表格等,同時還有一定幾率包括一些XML的關(guān)鍵字和XML標記的左右括號等,所以使用XML進行傳輸可能會出現(xiàn)一定的問題。因此現(xiàn)有的加密算法不能解決這個問題[3]。
解決這個問題最關(guān)鍵的就是將圖片中的所有二進制轉(zhuǎn)換為可識別的二進制,即可以使用ASCII正常表示的,可以選用的包括大小寫字母和數(shù)字。
在《一種基于XML的圖像存儲方法》一文中,所提出的方法是使用的是2個字節(jié)表示一個二進制碼的辦法,從而使一個字節(jié)變成了2個字符的表示方式,而在長度上,其容量增加了一倍。如果在大量的數(shù)據(jù)傳輸,那么增加的一倍會降低傳輸效率,同時也會導(dǎo)致數(shù)據(jù)傳輸時間的加長[4]。
因此,本方提出了一種新方法,減少轉(zhuǎn)換后的數(shù)據(jù)量,從而增加傳輸效率。由于二進制中可顯示的碼元有限,常見的只有48-59,65-90,97-122這62的可用碼元。要表示一個字節(jié)的二進制完全是不夠的。
由于3個可見碼元空間是62*62*62 = 238328>65536=256*256,所以可以采取用3個可見碼元表示2個二進制數(shù)據(jù)的方法,從而減少了冗余數(shù)據(jù)量。
另外,由于52個碼元的效果和62的碼元的效果在減少碼元長度上并沒有區(qū)別,因為3個52進制編碼所表示的范圍是:52*52*52=140608>65536,即三個52進制的碼元是可以完全包括4位16進制編碼三元的,所以從簡化的角度出發(fā),只使用大小寫字母的52個碼元,不再使用數(shù)數(shù)字。當然,如果仍然使用數(shù)據(jù)除了計算上略有影響,與只使用字母沒有任何區(qū)別。
將圖片文件中的數(shù)據(jù)的每個字節(jié)轉(zhuǎn)換成可識別的ASCII碼,本方法將2字節(jié)二進制數(shù)據(jù)轉(zhuǎn)換為3的52進制編碼,計算方法如下:
1)設(shè)2字節(jié)的二進制編碼為B1 B2,那么可以計算出其對應(yīng)的十進制編碼
D10 =B1*256+B2。 (D表示10進制編碼,B1表示原碼高位,B2表示原碼低位)
2)將十進制轉(zhuǎn)換為52進制,轉(zhuǎn)換方法采取余的方式,轉(zhuǎn)換后會有三位52進制碼,轉(zhuǎn)換公式如下:
bl = D10 % 52(bl表示低位)
bm = (D10 / 52) % 52 (bm表示中間位)
bh = (D10 / 52) / 52(bh表示高位)
3)將52進制轉(zhuǎn)換為對應(yīng)的大小寫字母,轉(zhuǎn)換方法如下:
C = C + 65 C∈[0, 25]
C + 97 - 26 C∈[26, 51]
4)將交換好的值,用對應(yīng)的ASCII碼表示。
即0-65535對應(yīng)三位的大小寫字母,如00 00對應(yīng)AAA,F(xiàn)F FF 對應(yīng)XLO。根據(jù)以上原理編,下面筆者使用程序語言進行編程,以對設(shè)計結(jié)果進行驗證(以下代碼均以C#代碼為例)。
二進制的數(shù)據(jù)是以字節(jié)數(shù)據(jù)的進行讀取過來,然后傳遞到程序中進行數(shù)據(jù)處理,所使用的數(shù)據(jù)轉(zhuǎn)換程序如下所示。
//用于編碼的函數(shù)
public string Encode(byte[] bts)
{
//建立變長數(shù)組,用于保存數(shù)據(jù)
StringBuilder builder = new StringBuilder();
int len = bts.Length / 2;
for (int i = 0; i < len; i++)
{
int t = bts[i] * 256 + bts[i + 1];
int v0 = t % 52;
t = t / 52;
int v1 = t % 52;
t = t / 52;
int v2 = t;
builder.Append(Transfer(v0));
builder.Append(Transfer(v1));
builder.Append(Transfer(v2));
}
return builder.ToString();
}
private string Transfer(int v)
{
v = v < 26 ? v + 65 : v + 97 - 26;
return ((char)v).ToString();
}
轉(zhuǎn)換時先轉(zhuǎn)換成52進制的編碼,然后再根據(jù)0-25轉(zhuǎn)換成A-Z,26-51轉(zhuǎn)換成a-z的規(guī)則,將所有轉(zhuǎn)換好的數(shù)值轉(zhuǎn)換成字母。
加密后的數(shù)據(jù)以字符串的形式存在,讀取后傳遞到程序中進行數(shù)據(jù)處理,所使用的數(shù)據(jù)轉(zhuǎn)換程序如下所示。
//用于解碼的函數(shù)。
public byte[] Decode(string s)
{
//建立用于保存二進制數(shù)據(jù)的數(shù)組。
byte[] bts = new byte[s.Length % 3];
int length = s.Length / 3;
//循環(huán)控制,
for (int i = 0; i < length; i++)
{
int t = Transfer1(s[i]) +
Transfer1(s[i + 1]) * 52 +
Transfer1(s[i + 2]) * 52 * 52;
bts[i] = (byte)(t / 256);
bts[i + 1] = (byte)(t % 256);
}
return bts;
}
private int Transfer1(char c)
{
int v = (int)c;
return v > 90 ? v - 97 + 32 : v - 65;
}
三位字符對應(yīng)的值為A-Z對應(yīng)0-25,a-z對應(yīng)26-51,轉(zhuǎn)換好以的三位a1,a2,a3再按照以下公式進行計算,從而還原原來的值。
計算公式為原先公式的逆運行,分為以下幾步:
1)將大小寫字母轉(zhuǎn)換成52進制的數(shù)據(jù)。
2)將52進制的數(shù)據(jù)轉(zhuǎn)換為10進制,公式為
b = a3*52*52 + a2 * 52 + a1,其中b為原值。
3)將10進制轉(zhuǎn)換為二進制
從原始的二進制的數(shù)據(jù)里可以看到,原始數(shù)據(jù)中里包含著如“<”, “>”等大量這樣的非字符碼元,這些非法碼元的存在有著很大的安全隱患,很可能會導(dǎo)致整個XML數(shù)據(jù)模塊的解析失敗,從而使原有XML文件的相關(guān)數(shù)據(jù)被二進制編碼所破壞。
現(xiàn)在采取將《一種基于XML的圖像存儲方法》一文中的方法將其轉(zhuǎn)換后,以小寫字母和數(shù)字的形式出現(xiàn),重新編碼后的XML文件如下所示。這樣經(jīng)過編碼以后,再使用XML就不會出現(xiàn)任何問題,但是長度比較度,為原來長度的2倍。于是采取本方中的新的編碼方式,結(jié)果如下所示。
經(jīng)過編碼以后,XML的傳輸就不會出現(xiàn)任何問題,但是長度比較度,為原來長度的2倍。在采取本方中的新的編碼方式,結(jié)果如下所示。
采用新的編碼以后,碼元的長度大大減少,達到了預(yù)期的目的。
本方提出了一種方法,將二進制的圖片轉(zhuǎn)換為可識別的字符串的,從而實現(xiàn)了在XML中傳輸圖片。同時采用新的算法,較《一種基于XML的圖像存儲方法》一文中的方法大幅提高了算法的效率,兼顧了效率,減少了存儲的容量,提高了傳輸效率。
[參 考 文 獻]
[1] 郝 偉.一種基于XML的圖像存儲方法[J].電腦技術(shù)與應(yīng)用, 2011(5).
[2] Steve Holzner. Inside XML[M].WROX PR,2000.
[3] Andrew Troelsen. Advcenced C# & .NET Program Design 4.0[M].北京:人民郵電出版社,2010.
[4] 李家同.算法設(shè)計與分析導(dǎo)論[M].北京:機械工業(yè)出版社,2008.
[5] 呂國英.算法設(shè)計與分析(第2版)[M]. 北京:清華大學(xué)出版社,2009.