99999久久久久久亚洲,欧美人与禽猛交狂配,高清日韩av在线影院,一个人在线高清免费观看,啦啦啦在线视频免费观看www

熱線電話:13121318867

登錄
首頁精彩閱讀EXCEL大數(shù)據(jù)量導(dǎo)出的解決方案
EXCEL大數(shù)據(jù)量導(dǎo)出的解決方案
2017-11-17
收藏

EXCEL大數(shù)據(jù)量導(dǎo)出的解決方案

將web頁面上顯示的報(bào)表導(dǎo)出到excel文件里是一種很常見的需求。潤(rùn)乾報(bào)表的類excel模型,支持excel文件數(shù)據(jù)無失真的導(dǎo)入導(dǎo)出,使用起來非常的方便。然而,當(dāng)數(shù)據(jù)量較大的情況下,excel本身的支持最多65535行數(shù)據(jù)的問題便凸顯出來。下面就給出大數(shù)據(jù)量導(dǎo)出到excel的解決方案。


首先,對(duì)于數(shù)據(jù)超過了65535行的問題,很自然的就會(huì)想到將整個(gè)數(shù)據(jù)分塊,利用excel的多sheet頁的功能,將超出65535行后的數(shù)據(jù)寫入到下一個(gè)sheet頁中,即通過多sheet頁的方式,突破了最高65535行數(shù)據(jù)的限定。

具體做法就是:

單獨(dú)做一個(gè)鏈接,使用JSP導(dǎo)出,在JSP上通過程序判斷報(bào)表行數(shù),超過65535行后分SHEET寫入。這樣這個(gè)問題就得以解決了。

更進(jìn)一步地說,在這種大數(shù)據(jù)量的報(bào)表生成和導(dǎo)出中,要占用大量的內(nèi)存,尤其是在使用TOMCAT的情況下,JVM最高只能支持到2G內(nèi)存,則會(huì)發(fā)生內(nèi)存溢出的情況。此時(shí)的內(nèi)存開銷主要是兩部分,一部分是該報(bào)表生成時(shí)的開銷,另一部分是該報(bào)表生成后寫入一個(gè)EXCEL時(shí)的開銷。由于JVM的GC機(jī)制是不能強(qiáng)制回收的,因此,對(duì)于此種情形,我們給出一個(gè)變通的解決方案。

首先,將該報(bào)表設(shè)置起始行和結(jié)束行參數(shù),在API生成報(bào)表的過程中,分步計(jì)算報(bào)表,比如一張20萬行數(shù)據(jù)的報(bào)表,在生成過程中,可通過起始行和結(jié)束行分4-5次進(jìn)行。這樣,就降低了報(bào)表生成時(shí)的內(nèi)存占用,在后面報(bào)表生成的過程中,如果發(fā)現(xiàn)內(nèi)存不夠,即可自動(dòng)啟動(dòng)JVM的GC機(jī)制,回收前面報(bào)表的緩存。

導(dǎo)出EXCEL的過程,放在每段生成報(bào)表之后立即進(jìn)行,改多個(gè)SHEET頁為多個(gè)EXCEL,即在分步生成報(bào)表的同時(shí)分步生成EXCEL,則通過POI包生成EXCEL的內(nèi)存消耗也得以降低。通過多次生成,同樣可以在后面EXCEL生成所需要的內(nèi)存不足時(shí),有效回收前面生成EXCEL時(shí)占用的內(nèi)存。

再使用文件操作,對(duì)每個(gè)客戶端的導(dǎo)出請(qǐng)求在服務(wù)器端根據(jù)SESSIONID和登陸時(shí)間生成唯一的臨時(shí)目錄,用來放置所生成的多個(gè)EXCEL,然后調(diào)用系統(tǒng)控制臺(tái),打包多個(gè)EXCEL為RAR或者JAR方式,最終反饋給用戶一個(gè)RAR包或者JAR包,響應(yīng)客戶請(qǐng)求后,再次調(diào)用控制臺(tái)刪除該臨時(shí)目錄。

使用這種方法,首先是通過分段運(yùn)算和生成,有效降低了報(bào)表從生成結(jié)果到生成EXCEL的內(nèi)存開銷。其次是通過使用壓縮包,響應(yīng)給用戶的生成文件體積大大縮小,降低了多用戶并發(fā)訪問時(shí)服務(wù)器下載文件的負(fù)擔(dān),有效減少多個(gè)用戶導(dǎo)出下載時(shí)服務(wù)器端的流量,從而達(dá)到進(jìn)一步減輕服務(wù)器負(fù)載的效果。


數(shù)據(jù)分析咨詢請(qǐng)掃描二維碼

若不方便掃碼,搜微信號(hào):CDAshujufenxi

數(shù)據(jù)分析師資訊
更多

OK
客服在線
立即咨詢
客服在線
立即咨詢
') } function initGt() { var handler = function (captchaObj) { captchaObj.appendTo('#captcha'); captchaObj.onReady(function () { $("#wait").hide(); }).onSuccess(function(){ $('.getcheckcode').removeClass('dis'); $('.getcheckcode').trigger('click'); }); window.captchaObj = captchaObj; }; $('#captcha').show(); $.ajax({ url: "/login/gtstart?t=" + (new Date()).getTime(), // 加隨機(jī)數(shù)防止緩存 type: "get", dataType: "json", success: function (data) { $('#text').hide(); $('#wait').show(); // 調(diào)用 initGeetest 進(jìn)行初始化 // 參數(shù)1:配置參數(shù) // 參數(shù)2:回調(diào),回調(diào)的第一個(gè)參數(shù)驗(yàn)證碼對(duì)象,之后可以使用它調(diào)用相應(yīng)的接口 initGeetest({ // 以下 4 個(gè)配置參數(shù)為必須,不能缺少 gt: data.gt, challenge: data.challenge, offline: !data.success, // 表示用戶后臺(tái)檢測(cè)極驗(yàn)服務(wù)器是否宕機(jī) new_captcha: data.new_captcha, // 用于宕機(jī)時(shí)表示是新驗(yàn)證碼的宕機(jī) product: "float", // 產(chǎn)品形式,包括:float,popup width: "280px", https: true // 更多配置參數(shù)說明請(qǐng)參見:http://docs.geetest.com/install/client/web-front/ }, handler); } }); } function codeCutdown() { if(_wait == 0){ //倒計(jì)時(shí)完成 $(".getcheckcode").removeClass('dis').html("重新獲取"); }else{ $(".getcheckcode").addClass('dis').html("重新獲取("+_wait+"s)"); _wait--; setTimeout(function () { codeCutdown(); },1000); } } function inputValidate(ele,telInput) { var oInput = ele; var inputVal = oInput.val(); var oType = ele.attr('data-type'); var oEtag = $('#etag').val(); var oErr = oInput.closest('.form_box').next('.err_txt'); var empTxt = '請(qǐng)輸入'+oInput.attr('placeholder')+'!'; var errTxt = '請(qǐng)輸入正確的'+oInput.attr('placeholder')+'!'; var pattern; if(inputVal==""){ if(!telInput){ errFun(oErr,empTxt); } return false; }else { switch (oType){ case 'login_mobile': pattern = /^1[3456789]\d{9}$/; if(inputVal.length==11) { $.ajax({ url: '/login/checkmobile', type: "post", dataType: "json", data: { mobile: inputVal, etag: oEtag, page_ur: window.location.href, page_referer: document.referrer }, success: function (data) { } }); } break; case 'login_yzm': pattern = /^\d{6}$/; break; } if(oType=='login_mobile'){ } if(!!validateFun(pattern,inputVal)){ errFun(oErr,'') if(telInput){ $('.getcheckcode').removeClass('dis'); } }else { if(!telInput) { errFun(oErr, errTxt); }else { $('.getcheckcode').addClass('dis'); } return false; } } return true; } function errFun(obj,msg) { obj.html(msg); if(msg==''){ $('.login_submit').removeClass('dis'); }else { $('.login_submit').addClass('dis'); } } function validateFun(pat,val) { return pat.test(val); }