JavaScript讀二進位文件並用ajax傳輸二進位流

来源:http://www.cnblogs.com/ljzc002/archive/2016/07/18/5681277.html
-Advertisement-
Play Games

使用JavaScript讀二進位文件並用ajax傳輸二進位流,目前能夠相容谷歌、IE11、IE10。 ...


綜合網上多個教程,加上自己實踐得出的方法,目前能夠相容谷歌、IE11、IE10。

htmlbody里的內容,沒什麼特殊的。

1 <div id="dConfirm">
2     <p style="float: left;margin-left: 20px;margin-top: 20px">
3         <form action="javascript: uploadAndSubmit();" name="demoForm" id="demoForm" method="post" enctype="multipart/form-data">
4             <p>上傳文件: <input type="file" name="file" id="str_file"/></p>
5             <p><input type="submit" value="上傳" /></p>
6         </form>
7     </p>
8 </div>
View Code

讀取二進位文件:

 1 function uploadAndSubmit()
 2     {
 3         filename=document.getElementById("str_file").value;
 4         var form = document.forms["demoForm"];
 5         if(filename!="")
 6         {
 7             try
 8             {
 9                 var obj = new ActiveXObject("ADODB.Stream");//這個必然是IE
10             }
11             catch(e)
12             {
13                 var file = form["file"].files[0];
14                 var reader = new FileReader();
15                 reader.readAsBinaryString(file);//這個讀法是非同步的
16 
17                 reader.onloadend=function()
18                 {
19                     // 這個事件在讀取結束後,無論成功或者失敗都會觸發
20                     if (reader.error) {
21                         console.log(reader.error);
22                     } else {
23                         uploadAndSubmit2(reader.result);
24                     }
25                 }
26                 return;
27             }
28             var bf1=new BinaryFile(filename);//這個讀法是同步的
29             uploadAndSubmit2(bf1.ReadAll());
30         }
31     }

這裡要對瀏覽器類型做一下判斷,如果不是IE則使用FileReader進行讀取,如果是IE則使用activex控制項讀取。這裡有一個坑,雖然IE11和IE10不支持FileReader對象的方法,但IE11和IE10的“typeof FileReader”並不是“undefined”,難以直接通過是否支持FileReader來區分瀏覽器。還要註意的是FileReader方法是非同步讀文件,activex是同步讀文件,我一直沒想明白這兩條路線怎樣封裝在一個方法里,不知大家有沒有好辦法。

其中BinaryFile對象的構造方法摘自http://www.codeproject.com/Articles/17825/Reading-and-Writing-Binary-Files-Using-JScript?msg=3718403#xx3718403xx技術博客,在博客的回覆中有一個改進方法據說效率更高,但因為沒有看懂,所以選用了原始方法。

原始方法很長:

  1 //使用ADODB.Stream控制項時要註意ISO-8859-1和Windows-1252字元集之間的轉換
  2 function BinaryFile(name)
  3 {
  4     var adTypeBinary = 1
  5     var adTypeText   = 2
  6     var adSaveCreateOverWrite = 2
  7     // The trick - this is the 'old fassioned' not translation page
  8     // It lest javascript use strings to act like raw octets
  9     var codePage='437';
 10 
 11     this.path=name;
 12 
 13     var forward  = new Array();
 14     var backward = new Array();
 15 
 16     // Note - for better performance I should preconvert these hex
 17     // definitions to decimal - at some point :-) - AJT
 18     forward['80'] = '00C7';
 19     forward['81'] = '00FC';
 20     forward['82'] = '00E9';
 21     forward['83'] = '00E2';
 22     forward['84'] = '00E4';
 23     forward['85'] = '00E0';
 24     forward['86'] = '00E5';
 25     forward['87'] = '00E7';
 26     forward['88'] = '00EA';
 27     forward['89'] = '00EB';
 28     forward['8A'] = '00E8';
 29     forward['8B'] = '00EF';
 30     forward['8C'] = '00EE';
 31     forward['8D'] = '00EC';
 32     forward['8E'] = '00C4';
 33     forward['8F'] = '00C5';
 34     forward['90'] = '00C9';
 35     forward['91'] = '00E6';
 36     forward['92'] = '00C6';
 37     forward['93'] = '00F4';
 38     forward['94'] = '00F6';
 39     forward['95'] = '00F2';
 40     forward['96'] = '00FB';
 41     forward['97'] = '00F9';
 42     forward['98'] = '00FF';
 43     forward['99'] = '00D6';
 44     forward['9A'] = '00DC';
 45     forward['9B'] = '00A2';
 46     forward['9C'] = '00A3';
 47     forward['9D'] = '00A5';
 48     forward['9E'] = '20A7';
 49     forward['9F'] = '0192';
 50     forward['A0'] = '00E1';
 51     forward['A1'] = '00ED';
 52     forward['A2'] = '00F3';
 53     forward['A3'] = '00FA';
 54     forward['A4'] = '00F1';
 55     forward['A5'] = '00D1';
 56     forward['A6'] = '00AA';
 57     forward['A7'] = '00BA';
 58     forward['A8'] = '00BF';
 59     forward['A9'] = '2310';
 60     forward['AA'] = '00AC';
 61     forward['AB'] = '00BD';
 62     forward['AC'] = '00BC';
 63     forward['AD'] = '00A1';
 64     forward['AE'] = '00AB';
 65     forward['AF'] = '00BB';
 66     forward['B0'] = '2591';
 67     forward['B1'] = '2592';
 68     forward['B2'] = '2593';
 69     forward['B3'] = '2502';
 70     forward['B4'] = '2524';
 71     forward['B5'] = '2561';
 72     forward['B6'] = '2562';
 73     forward['B7'] = '2556';
 74     forward['B8'] = '2555';
 75     forward['B9'] = '2563';
 76     forward['BA'] = '2551';
 77     forward['BB'] = '2557';
 78     forward['BC'] = '255D';
 79     forward['BD'] = '255C';
 80     forward['BE'] = '255B';
 81     forward['BF'] = '2510';
 82     forward['C0'] = '2514';
 83     forward['C1'] = '2534';
 84     forward['C2'] = '252C';
 85     forward['C3'] = '251C';
 86     forward['C4'] = '2500';
 87     forward['C5'] = '253C';
 88     forward['C6'] = '255E';
 89     forward['C7'] = '255F';
 90     forward['C8'] = '255A';
 91     forward['C9'] = '2554';
 92     forward['CA'] = '2569';
 93     forward['CB'] = '2566';
 94     forward['CC'] = '2560';
 95     forward['CD'] = '2550';
 96     forward['CE'] = '256C';
 97     forward['CF'] = '2567';
 98     forward['D0'] = '2568';
 99     forward['D1'] = '2564';
100     forward['D2'] = '2565';
101     forward['D3'] = '2559';
102     forward['D4'] = '2558';
103     forward['D5'] = '2552';
104     forward['D6'] = '2553';
105     forward['D7'] = '256B';
106     forward['D8'] = '256A';
107     forward['D9'] = '2518';
108     forward['DA'] = '250C';
109     forward['DB'] = '2588';
110     forward['DC'] = '2584';
111     forward['DD'] = '258C';
112     forward['DE'] = '2590';
113     forward['DF'] = '2580';
114     forward['E0'] = '03B1';
115     forward['E1'] = '00DF';
116     forward['E2'] = '0393';
117     forward['E3'] = '03C0';
118     forward['E4'] = '03A3';
119     forward['E5'] = '03C3';
120     forward['E6'] = '00B5';
121     forward['E7'] = '03C4';
122     forward['E8'] = '03A6';
123     forward['E9'] = '0398';
124     forward['EA'] = '03A9';
125     forward['EB'] = '03B4';
126     forward['EC'] = '221E';
127     forward['ED'] = '03C6';
128     forward['EE'] = '03B5';
129     forward['EF'] = '2229';
130     forward['F0'] = '2261';
131     forward['F1'] = '00B1';
132     forward['F2'] = '2265';
133     forward['F3'] = '2264';
134     forward['F4'] = '2320';
135     forward['F5'] = '2321';
136     forward['F6'] = '00F7';
137     forward['F7'] = '2248';
138     forward['F8'] = '00B0';
139     forward['F9'] = '2219';
140     forward['FA'] = '00B7';
141     forward['FB'] = '221A';
142     forward['FC'] = '207F';
143     forward['FD'] = '00B2';
144     forward['FE'] = '25A0';
145     forward['FF'] = '00A0';
146     backward['C7']   = '80';
147     backward['FC']   = '81';
148     backward['E9']   = '82';
149     backward['E2']   = '83';
150     backward['E4']   = '84';
151     backward['E0']   = '85';
152     backward['E5']   = '86';
153     backward['E7']   = '87';
154     backward['EA']   = '88';
155     backward['EB']   = '89';
156     backward['E8']   = '8A';
157     backward['EF']   = '8B';
158     backward['EE']   = '8C';
159     backward['EC']   = '8D';
160     backward['C4']   = '8E';
161     backward['C5']   = '8F';
162     backward['C9']   = '90';
163     backward['E6']   = '91';
164     backward['C6']   = '92';
165     backward['F4']   = '93';
166     backward['F6']   = '94';
167     backward['F2']   = '95';
168     backward['FB']   = '96';
169     backward['F9']   = '97';
170     backward['FF']   = '98';
171     backward['D6']   = '99';
172     backward['DC']   = '9A';
173     backward['A2']   = '9B';
174     backward['A3']   = '9C';
175     backward['A5']   = '9D';
176     backward['20A7'] = '9E';
177     backward['192']  = '9F';
178     backward['E1']   = 'A0';
179     backward['ED']   = 'A1';
180     backward['F3']   = 'A2';
181     backward['FA']   = 'A3';
182     backward['F1']   = 'A4';
183     backward['D1']   = 'A5';
184     backward['AA']   = 'A6';
185     backward['BA']   = 'A7';
186     backward['BF']   = 'A8';
187     backward['2310'] = 'A9';
188     backward['AC']   = 'AA';
189     backward['BD']   = 'AB';
190     backward['BC']   = 'AC';
191     backward['A1']   = 'AD';
192     backward['AB']   = 'AE';
193     backward['BB']   = 'AF';
194     backward['2591'] = 'B0';
195     backward['2592'] = 'B1';
196     backward['2593'] = 'B2';
197     backward['2502'] = 'B3';
198     backward['2524'] = 'B4';
199     backward['2561'] = 'B5';
200     backward['2562'] = 'B6';
201     backward['2556'] = 'B7';
202     backward['2555'] = 'B8';
203     backward['2563'] = 'B9';
204     backward['2551'] = 'BA';
205     backward['2557'] = 'BB';
206     backward['255D'] = 'BC';
207     backward['255C'] = 'BD';
208     backward['255B'] = 'BE';
209     backward['2510'] = 'BF';
210     backward['2514'] = 'C0';
211     backward['2534'] = 'C1';
212     backward['252C'] = 'C2';
213     backward['251C'] = 'C3';
214     backward['2500'] = 'C4';
215     backward['253C'] = 'C5';
216     backward['255E'] = 'C6';
217     backward['255F'] = 'C7';
218     backward['255A'] = 'C8';
219     backward['2554'] = 'C9';
220     backward['2569'] = 'CA';
221     backward['2566'] = 'CB';
222     backward['2560'] = 'CC';
223     backward['2550'] = 'CD';
224     backward['256C'] = 'CE';
225     backward['2567'] = 'CF';
226     backward['2568'] = 'D0';
227     backward['2564'] = 'D1';
228     backward['2565'] = 'D2';
229     backward['2559'] = 'D3';
230     backward['2558'] = 'D4';
231     backward['2552'] = 'D5';
232     backward['2553'] = 'D6';
233     backward['256B'] = 'D7';
234     backward['256A'] = 'D8';
235     backward['2518'] = 'D9';
236     backward['250C'] = 'DA';
237     backward['2588'] = 'DB';
238     backward['2584'] = 'DC';
239     backward['258C'] = 'DD';
240     backward['2590'] = 'DE';
241     backward['2580'] = 'DF';
242     backward['3B1']  = 'E0';
243     backward['DF']   = 'E1';
244     backward['393']  = 'E2';
245     backward['3C0']  = 'E3';
246     backward['3A3']  = 'E4';
247     backward['3C3']  = 'E5';
248     backward['B5']   = 'E6';
249     backward['3C4']  = 'E7';
250     backward['3A6']  = 'E8';
251     backward['398']  = 'E9';
252     backward['3A9']  = 'EA';
253     backward['3B4']  = 'EB';
254     backward['221E'] = 'EC';
255     backward['3C6']  = 'ED';
256     backward['3B5']  = 'EE';
257     backward['2229'] = 'EF';
258     backward['2261'] = 'F0';
259     backward['B1']   = 'F1';
260     backward['2265'] = 'F2';
261     backward['2264'] = 'F3';
262     backward['2320'] = 'F4';
263     backward['2321'] = 'F5';
264     backward['F7']   = 'F6';
265     backward['2248'] = 'F7';
266     backward['B0']   = 'F8';
267     backward['2219'] = 'F9';
268     backward['B7']   = 'FA';
269     backward['221A'] = 'FB';
270     backward['207F'] = 'FC';
271     backward['B2']   = 'FD';
272     backward['25A0'] = 'FE';
273     backward['A0']   = 'FF';
274 
275     var hD="0123456789ABCDEF";
276     this.d2h = function(d)
277     {
278         var h = hD.substr(d&15,1);
279         while(d>15) {d>>=4;h=hD.substr(d&15,1)+h;}
280         return h;
281     }
282 
283     this.h2d = function(h)
284     {
285         return parseInt(h,16);
286     }
287 
288     this.WriteAll = function(what)
289     {
290         //Create Stream object
291         //var BinaryStream = WScript.CreateObject("ADODB.Stream");
292         var BinaryStream = new ActiveXObject("ADODB.Stream");
293         //Specify stream type - we cheat and get string but 'like' binary
294         BinaryStream.Type = adTypeText;
295         BinaryStream.CharSet = '437';
296         //Open the stream
297         BinaryStream.Open();
298         // Write to the stream
299         BinaryStream.WriteText(this.Forward437(what));
300         // Write the string to the disk
301         BinaryStream.SaveToFile(this.path, adSaveCreateOverWrite);
302 
303         // Clearn up
304         BinaryStream.Close();
305     }
306 
307     this.ReadAll  = function()
308     {
309         //Create Stream object - needs ADO 2.5 or heigher
310         //var BinaryStream = WScript.CreateObject("ADODB.Stream")
311         var BinaryStream = new ActiveXObject("ADODB.Stream");
312         //Specify stream type - we cheat and get string but 'like' binary
313         BinaryStream.Type = adTypeText;
314         BinaryStream.CharSet = codePage;
315         //Open the stream
316         BinaryStream.Open();
317         //Load the file data from disk To stream object
318         BinaryStream.LoadFromFile(this.path);
319         //Open the stream And get binary 'string' from the object
320         var what = BinaryStream.ReadText;
321         // Clean up
322         BinaryStream.Close();
323         return this.Backward437(what);
324     }
325 
326     /* Convert a octet number to a code page 437 char code */
327     this.Forward437 = function(inString)
328     {
329         var encArray = new Array();
330         var tmp='';
331         var i=0;
332         var c=0;
333         var l=inString.length;
334         var cc;
335         var h;
336         for(;i<l;++i)
337         {
338             c++;
339             if(c==128)
340             {
341                 encArray.push(tmp);
342                 tmp='';
343                 c=0;
344             }
345             cc=inString.charCodeAt(i);
346             if(cc<128)
347             {
348                 tmp+=String.fromCharCode(cc);
349             }
350             else
351             {
352                 h=this.d2h(cc);
353                 h=forward[''+h];
354                 tmp+=String.fromCharCode(this.h2d(h));
355             }
356         }
357         if(tmp!='')
358         {
359             encArray.push(tmp);
360         }
361 
362         // this loop progressive concatonates the
363         // array elements entil there is only one
364         var ar2=new Array();
365         for(;encArray.length>1;)
366         {
367             var l=encArray.length;
368             for(var c=0;c<l;c+=2)
369             {
370                 if(c+1==l)
371                 {
372                     ar2.push(encArray[c]);
373                 }
374                 else
375                 {
376                     ar2.push(''+encArray[c]+encArray[c+1]);
377                 }
378             }
379             encArray=ar2;
380             ar2=new Array();
381         }
382         return encArray[0];
383     }
384     /* Convert a code page 437 char code to a octet number*/
385     this.Backward437 = function(inString)
386     {
387         var encArray = new Array();
388         var tmp='';
389         var i=0;
390         var c=0;
391         var l=inString.length;
392         var cc;
393         var h;
394         for(;i<l;++i)
395         {
396             c++;
397             if(c==128)
398             {
399                 encArray.push(tmp);
400                 tmp='';
401                 c=0;
402             }
403             cc=inString.charCodeAt(i);
404             if(cc<128)
405             {
406                 tmp+=String.fromCharCode(cc);
407             }
408             else
409             {
410                 h=this.d2h(cc);
411                 h=backward[''+h];
412                 tmp+=String.fromCharCode(this.h2d(h));
413             }
414         }
415         if(tmp!='')
416         {
417             encArray.push(tmp);
418         }
419 
420         // this loop progressive concatonates the
421         // array elements entil there is only one
422         var ar2=new Array();
423         for(;encArray.length>1;)
424         {
425             var l=encArray.length;
426             for(var c=0;c<l;c+=2)
427             {
428                 if(c+1==l)
429                 {
430                     ar2.push(encArray[c]);
431                 }
432                 else
433                 {
434                     ar2.push(''+encArray[c]+encArray[c+1]);
435                 }
436             }
437             encArray=ar2;
438             ar2=new Array();
439         }
440         return encArray[0];
441     }
442 }
View Code

其中主體部分是:

 1 this.ReadAll  = function()
 2     {
 3         //Create Stream object - needs ADO 2.5 or heigher
 4         //var BinaryStream = WScript.CreateObject("ADODB.Stream")
 5         var BinaryStream = new ActiveXObject("ADODB.Stream");
 6         //Specify stream type - we cheat and get string but 'like' binary
 7         BinaryStream.Type = adTypeText;
 8         BinaryStream.CharSet = codePage;
 9         //Open the stream
10         BinaryStream.Open();
11         //Load the file data from disk To stream object
12         BinaryStream.LoadFromFile(this.path);
13         //Open the stream And get binary 'string' from the object
14         var what = BinaryStream.ReadText;
15         // Clean up
16         BinaryStream.Close();
17         return this.Backward437(what);
18     }

這裡就是使用"ADODB.Stream"控制項讀取文件的方法,可以看到作者使用的讀取類型是adTypeText(2),是在用文本讀取方式讀二進位文件!而按照文檔改為adTypeBinary(1)類型後則讀不到任何內容,不知道是為什麼。

其餘部分代碼則是在做編碼轉換工作,大體意思是讀文件時要使用“ISO-8859-1”字元集,用http發送文件時則要使用“Windows-1252”字元集,這兩種字元集只有極少數字元有差別,所以在讀到的數據中找到有區別的部分一一轉換為另一種字元集表示。

ajax發送二進位流:

 1 function uploadAndSubmit2(BinaryContent)
 2     {
 3         Url = UrlHead + "Cook.ashx";
 4         xmlHttp=new XMLHttpRequest();
 5         xmlHttp.open("POST",Url + "?method=post&func=file_upload&fileName=" + encodeURIComponent(filename.split("\\")[filename.split("\\").length-1]));//IE處理漢字url
 6         xmlHttp.sendAsBinary(BinaryContent);
 7         xmlHttp.onreadystatechange = function ()
 8         {
 9             if (xmlHttp.readyState == 4) {
10                 if (xmlHttp.status == 200) {
11                     var str=xmlHttp.response;
12                     alert(str);

              
您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 優秀程式設計的Kiss原則(keep it simple,stupid) 優秀程式設計的Kiss原則(keep it simple,stupid) 良好的編程原則與良好的設計工程原則密切相關。本文總結的這些設計原則,幫助開發者更有效率的編寫代碼,並幫助成為一名優秀的程式員。 1.避免重覆原則(DRY ...
  • 面向對象 問題 面向對象的好處 學一門技術是否需要趣味性、通俗性的指導 面向對象 什麼是對象 世間任何事物都可以定義為對象。 什麼是類 類就是把對象的公共屬性和方法抽離出來形成集合的抽象,也就是說,類是一種抽象,用來描述對象特征的抽象。 什麼是實例 實例就是對象,就好比我們,就是人這種抽象的一個實例 ...
  • 在本人寫的前一篇文章中,談及有關如何利用Netty開發實現,高性能RPC伺服器的一些設計思路、設計原理,以及具體的實現方案(具體參見:談談如何使用Netty開發實現高性能的RPC伺服器)。在文章的最後提及到,其實基於該方案設計的RPC伺服器的處理性能,還有優化的餘地。於是利用周末的時間,在原來Net ...
  • 場景 自己弄了一個 "個人站點" ,平時文章更多的是在博客園寫就,也懶得將博文搬走,於是想到做一個爬蟲將博文目錄結構以及分類爬取到自己的個人站點上,(雖然沒有,也算為博客園增加權重引流了)。 流程 思路是開一個子進程,每隔30分鐘爬取博客園自己個人的博文目錄和結構,保存到資料庫。再在跳到對應路由的時 ...
  • clip 屬性是用來設置元素的形狀。用來剪裁絕對定位元素(absolute or fixed)。 clip有三種取值:auto |inherit|rect。inherit是繼承,ie不支持這個屬性, auto是預設 前兩個基本屬於打醬油的,我們主要來說一下clip的rect屬性。 clip的rect ...
  • 上周看到大家在JS群討論如何把一句英文句子單詞收割字母大寫,大家都說用正則簡單,對於正則還是有點模糊,於是乎自己敲了下 結果是出來了,總感覺不是很好、、、 ...
  • 使用方法:在JS包的說明裡;直接使用例子也是可以的 起因:一直以來,移動端選擇器都是自己在網上滿世界的找插件 缺點: 1.前期需要自己找非常多的插件,進行篩選;浪費了自己大量的時間 2.符合要求的少之又少,能最後用上的就更少了; 3.項目有特殊要求,又要符合設計稿,難上加難; 所以,這次自己寫了一個 ...
  • 通過packet capture對舊版的第三方app進行抓包分析以後,能夠獲取cnblogs對app開放的一些api。 簡要介紹直接和網站文章內容相關的api。 希望更多精美的第三方app能夠出現 :) host:http://www.cnblogs.com endpoint:/mvc/aggsit ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...