經過了一天的研究之後,把想到的東西寫出來,防止自己忘記,因爲太亂了...
首先,開始舉例:
public int getLen(Charset charset) {
int len = 2;
try {
//真實數據區
if (events != null && events.length > 0) {
for (int i = 0; i < events.length; i++) {
BattleFieldDto edt = events[i];
len += 2 + 4 + 1 + 1 + 1 + 1 +edt.getLen(charset);
}
}
} catch (Exception e) {
logger.error("錯誤...", e);
}
return len;
}
@Override
public int getDataOffset() {
int len = 1 + 4 + 2 ;
if (events != null && events.length > 0) {
len += events.length * (2 + 4 + 1 + 1 + 1 + 1);
}
return len;
}
}
這是一段response中的代碼片段,首先看getLen中的Len的定義,這裏寫的是Len = 2,因爲在events中的循環的關係,這個2其實是循環的次數的一個short,就是2位,專門存放循環用的;往下來,len += 2 + 4 + 1 + 1 + 1 + 1 +edt.getLen(charset);這裏的2 是一個short,4是存放String的offset的int,然後是String的長度爲1個byte,1是一個byte,1是一個byte,1是一個byte,後邊的edt.getLen(charset);是一個string,由於mina的協議String的存放有點說法,所以就加在了這裏,這裏應該是直接發包出去的實際的數據形式,也就是說除了報文頭和報文長度的有效傳輸包的長度。
而繼續看這個getDataOffset函數:
int len = 1 + 4 + 2 ;這裏的1是報文頭,4是報文長度,2和getLen裏的len定義時的2是一個東西,他倆應該是一致的。
接着看:
len += events.length * (2 + 4 + 1 + 1 + 1 + 1);
這裏的events就是報文的循環體了,但是注意,這裏和剛纔的2 + 4 + 1 + 1 + 1 + 1 +edt.getLen(charset);是一樣的,爲什麼呢,就是因爲String的特殊存儲方式,一個String的存儲是由4個字節的偏移量和1個字節的String的長度來構成的,取String的時候首先要getInt()取得4個字節的偏移量,在偏移量的下一個byte也就是get()出1個字節的String的長度,就可以getString(1個字節的長度,charset)取得String了。
說到這裏,特殊的就是4 + 1 ,這個代表了一個String,如果events中存在多個String,那麼這裏將是多個4 + 1,而在getLen中卻不會出現4+1,只會出現多個edt.getLen(charset);而已。
接下來就是request的:
public int getLen(Charset charset) {
int len = 4 + 1 + 1;
try {
if (player_nickname != null && !"".equals(player_nickname)) {
len += player_nickname.getBytes(charset).length;
}
} catch (Exception e) {
logger.error("錯誤...", e);
}
return len;
}
@Override
public int getDataOffset() {
int len = 1 + 4 + 4 + 1 + 1;
return len;
}
注意看,這裏的getLen中的len定義的時候是 4 + 1 + 1,分別是一個int,一個byte,和一個String的長度,長度是一個byte,如果這裏邊有String的話一定要多出來一個byte來記錄這個String的長度,如果有2個String的話要在後邊繼續添加一個byte,而String要統一放在最後邊一起進行相加,還是協議的關係,String類型不能放在基本數據區,只有java的8個原始數據類型纔可以放在基本數據區。
然後再看 getDataOffset,這裏的len定義的是:1是報文頭,4是報文長度,然後後邊的4 + 1 + 1就是getLen中的len定義的了,其他的跟response中的是一樣的。
就是這些,弄了一天,一直在寫字節數,自己手動算來算去的,麻煩死了。。