javascript模擬訂火車票和退票示例
之前看到有人分析12306后臺(tái)的邏輯。。火車票的預(yù)定和退訂不同于普通的購(gòu)物。
一個(gè)難題就是火車票可以分站來賣。比如,一張北京到上海的火車票,沿途可以有很多站,可以北京-濟(jì)南,濟(jì)南-南京...等等。如何設(shè)計(jì)數(shù)據(jù)模型來存取這些票是一個(gè)問題。而不是簡(jiǎn)單的數(shù)量+-1.
其中看到一條思路挺好:用二進(jìn)制字符串來表示一張火車票,比如,北京到上海共10站,那么一張全程票初始狀態(tài)表示為:'1111111111';
賣出一張全程票,則該票變?yōu)?0000000000';
賣出一張半程票,比如北京-濟(jì)南三站(第一站-第三站),則票變?yōu)?0011111111';
再賣出一張半程票,比如徐州-南京(第6站-第9站),則上一張票變?yōu)?'0011100011';
退訂票的邏輯就很簡(jiǎn)單了,我要退一張(徐州-南京)的票,則從票池中找到第一張不能買
(徐州-南京)的票,更改它就OK(買票的逆向).比如,找到了上面的一張票'0011100011',
退票后,此票變?yōu)?0011111111);
基本邏輯如上,12306要保證多入口,而同時(shí)數(shù)據(jù)的一致性,需要很高效的邏輯來處理查票,
買票,退票的業(yè)務(wù),據(jù)說高峰每秒會(huì)有20萬請(qǐng)求。將票的數(shù)據(jù)結(jié)構(gòu)保存在內(nèi)存中。而非數(shù)據(jù)庫(kù)。
小而高效的數(shù)據(jù)結(jié)變得很重要。
if(jQuery){}else{
//document.write
}
function Server(){
var self = this;
self.ticketsPool = [];
self._init= function(number){
if(typeof(number) != 'number')
throw ('type error');
for(i=0;i<number;i++){
self.ticketsPool.push(new Ticket());
}
};
//判斷一張票是否可以買,通過與或運(yùn)算來實(shí)現(xiàn)。
//比如:訂單o為北京-濟(jì)南(001111111),某張票為(0000000011)(已賣出北京-南京),那么返回false
//比如:訂單o為北京-濟(jì)南(001111111),某張票為(1111100011)(已賣出徐州-南京),那么返回true
self.canBuy = function(o,t){
var _o = ''
for(j=0; j<o.length; j++){
_o += o[j]=='0'?1:0;
}
var r1 = (parseInt(t.tic,2) | parseInt(o,2)) & parseInt(_o,2);
var r2 = parseInt(_o,2);
return r1 == r2;
};
//賣出一張票
self.pop1Ticket = function(o){
for(i=0;i < self.ticketsPool.length;i++){
if(self.canBuy(o,self.ticketsPool[i])){
self.buy(self.ticketsPool[i],o);
return i;
}
};
return -1;
};
//賣出票的實(shí)現(xiàn),改變二進(jìn)制字符串,比如'111111111'->'001111111';
self.buy = function(t,o){
t.tic = (parseInt(t.tic,2) & parseInt(o,2)).toString(2);
//alert(t.tic);
};
//查詢余票
self.remainTics = function(o){
var count=0;
for(i=0;i < self.ticketsPool.length;i++){
count += self.canBuy(o,self.ticketsPool[i])?1:0;
};
return count;
}
//退票,或 運(yùn)算
self.refund = function(o){
for(i=0;i < self.ticketsPool.length;i++){
if(!self.canBuy(o,self.ticketsPool[i])){
var _o = ''
for(j=0; j<o.length; j++){
_o += o[j]=='0'?1:0;
}
self.ticketsPool[i].tic = (parseInt(self.ticketsPool[i].tic,2) | parseInt(_o,2)).toString(2);
return i;
}
};
return -1;
}
}
//數(shù)據(jù)模型:票
function Ticket(){
var self = this;
//票的初始為全程票
self.tic = '1111111111';
}
//數(shù)據(jù)模型:訂單
function Order(from, to){
var self = this;
var s = '';
for(i=0;i<10;i++){
s += (i>=from && i<to)?0:1;
}
return s;
}
//12306后臺(tái)
Server = new Server();
//初始狀態(tài),票池有400張全程票
Server._init(400);
相關(guān)文章
JS中for循序中延遲加載動(dòng)態(tài)效果的具體實(shí)現(xiàn)
今天在做一個(gè)前端的效果的時(shí)候碰到一個(gè)棘手的問題,就是實(shí)現(xiàn)一個(gè)動(dòng)態(tài)的圓柱效果,廢話不多少,直接上代碼2013-08-08JS中構(gòu)造函數(shù)的基本特性與優(yōu)缺點(diǎn)
這篇文章介紹了JS中構(gòu)造函數(shù)的基本特性與優(yōu)缺點(diǎn),文中通過示例代碼介紹的非常詳細(xì)。對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2022-06-06javaScript parseInt字符轉(zhuǎn)化為數(shù)字函數(shù)使用小結(jié)
前幾天做網(wǎng)站的時(shí)候需要講數(shù)據(jù)庫(kù)中的時(shí)間讀取到變量中進(jìn)行使用,用到parseInt函數(shù),講字符轉(zhuǎn)化為數(shù)字。2009-11-11JavaScript sub方法入門實(shí)例(把字符串顯示為下標(biāo))
這篇文章主要介紹了JavaScript sub方法入門實(shí)例,sub方法用于把字符串顯示為下標(biāo),需要的朋友可以參考下2014-10-10js用Date對(duì)象處理時(shí)間實(shí)現(xiàn)思路及代碼
本文主要是為了解決從XML文件中讀取數(shù)據(jù),然后將里面的數(shù)據(jù)返回到頁面中用一個(gè)第三方插件進(jìn)行繪圖,并且提供了詳細(xì)的解決方法,感興趣的朋友可以了解下或許對(duì)你有所幫助2013-01-01