加快C#雙循環(huán)的速度效率的方法
一、前言
最近使用 C# 改寫(xiě)以前編的一個(gè)程序,檢索數(shù)據(jù)賦值時(shí),使用 FOR 循環(huán)結(jié)構(gòu),當(dāng)數(shù)據(jù)量在9萬(wàn)條時(shí),計(jì)算量很大,導(dǎo)致很耗時(shí),何況計(jì)算完成同時(shí)加載到 chart 和 dataGridView 圖表控件中(沒(méi)有使用第三方控件),于是百度了很多循環(huán)手段。
二、多種循環(huán)的速度效率
2.1、常用循環(huán)速度效率對(duì)比
循環(huán)結(jié)構(gòu)體 | 速度和效率 |
---|---|
for(int i=0;i<n;i++){} | 對(duì)于已知次數(shù)的迭代,使用 for 循環(huán)通常是最快的。 |
foreach(string S in Data){} | 適用于遍歷集合,如數(shù)組或列表,但通常比 for 循環(huán)慢,因?yàn)樗枰嗟拈g接訪問(wèn)。 |
while do-while | 適用于不確定次數(shù)的迭代,但可能在性能上不如 for 循環(huán)。 |
Parallel.For Parallel.ForEach Parallel.Invoke | 并行計(jì)算類(lèi),三個(gè)方法都會(huì)阻塞線程直到所有工作完成為止。僅當(dāng)適用時(shí)可采用,否則出現(xiàn)意外錯(cuò)誤。 Parallel.ForEach 比 Parallel.For 效率更高。 Parallel.Invoke 適合用于執(zhí)行大量且無(wú)返回值的場(chǎng)景; Parallel.For 使用是無(wú)序的,適合帶索引的大量循環(huán)操作; Parallel.ForEach 適合數(shù)組、集合、枚舉大數(shù)據(jù)集的循環(huán)執(zhí)行,執(zhí)行結(jié)果是無(wú)序的。 |
2.2、如何提高循環(huán)的速度效率
2.2.1、選擇合適的循環(huán)類(lèi)型
循環(huán)的效率通常取決于多個(gè)因素,包括循環(huán)的類(lèi)型、循環(huán)體內(nèi)的操作、以及循環(huán)的次數(shù)。選擇合適的循環(huán)類(lèi)型很重要。
2.2.2、減少循環(huán)體內(nèi)的操作
循環(huán)體內(nèi)的操作越少,循環(huán)的效率越高。例如,避免在每次迭代中進(jìn)行復(fù)雜的計(jì)算或方法調(diào)用。
2.2.3、使用局部變量而非頻繁訪問(wèn)成員
如果循環(huán)體內(nèi)需要多次訪問(wèn)對(duì)象的成員,最好將該成員的值存儲(chǔ)在局部變量中,這樣可以減少多次訪問(wèn)成員的開(kāi)銷(xiāo)。
2.2.4、避免在循環(huán)體內(nèi)進(jìn)行不必要的對(duì)象創(chuàng)建或銷(xiāo)毀
每次迭代創(chuàng)建新對(duì)象會(huì)增加GC(垃圾回收)的壓力,降低性能。如果可能,考慮對(duì)象池技術(shù)或復(fù)用對(duì)象。
2.2.5、僅當(dāng)適用時(shí)可采用并行處理
對(duì)于可以并行處理的計(jì)算任務(wù),使用 Parallel.For 或 PLINQ(Parallel LINQ)可以顯著提高性能,特別是當(dāng)處理大量數(shù)據(jù)時(shí)。然而,并行處理需要謹(jǐn)慎使用,因?yàn)樗鼤?huì)增加線程管理的開(kāi)銷(xiāo)。
三、如何提高雙循環(huán)計(jì)算速度效率的編程實(shí)例
遵循上述循環(huán)原則,對(duì)于有序的數(shù)據(jù)集,通過(guò)多次測(cè)試各種循環(huán),采用的 for 雙循環(huán)。
Hypack RAW 數(shù)據(jù)中,實(shí)時(shí)采集的定位 POS 數(shù)據(jù)和 EC1 數(shù)據(jù)系列,時(shí)間和位置大部分不同步,但處于同一個(gè)航線軌跡上,通過(guò)各采集點(diǎn)的時(shí)間秒、坐標(biāo)、水深,計(jì)算航行距離、航行速度,以計(jì)算插補(bǔ) EC1 采集數(shù)據(jù)所在定位坐標(biāo)。
POS 數(shù)據(jù)有時(shí)間、定位東和北坐標(biāo)數(shù)組,POSTime[]、POSEast[]、POSNorth[] 數(shù)據(jù)長(zhǎng)度一致。
EC1 數(shù)據(jù)有時(shí)間、水深數(shù)組,EC1Time[]、EC1WaterDepth[] 數(shù)據(jù)長(zhǎng)度一致。
POS 和 EC1 數(shù)據(jù)個(gè)數(shù)不對(duì)等。
還要根據(jù) FIX 和 EC1 數(shù)據(jù),插補(bǔ) FIX 采集數(shù)據(jù)點(diǎn)的水深,這里就不描述。
Hypack RAW 數(shù)據(jù)節(jié)選如下:
POS 0 37410.599 626291.650 3216635.552 QUA 0 37410.599 7 3.000 1.000 8.000 2.000 0.000 0.000 0.000 RAW 0 37410.599 4 290361.17840 1121780.82570 9.91600 22330.60000 MSG 0 37410.538 $GPGGA,022330.60,2903.611784,N,11217.808257,E,2,08,1.0,9.916,M,0.0,M,8.0,0643*71 MSG 0 37410.581 $GPVTG,22.3,T,,M,0.08,N,0.15,K,P*23 MSG 0 37410.600 $GPZDA,022330.60,27,03,2024,00,00*62 EC1 1 37410.736 1.040 POS 0 37410.799 626291.660 3216635.561 QUA 0 37410.799 7 3.000 1.000 8.000 2.000 0.000 0.000 0.000 RAW 0 37410.799 4 290361.17890 1121780.82630 9.90800 22330.80000 MSG 0 37410.735 $GPGGA,022330.80,2903.611789,N,11217.808263,E,2,08,1.0,9.908,M,0.0,M,8.0,0643*7A MSG 0 37410.778 $GPVTG,42.9,T,,M,0.15,N,0.27,K,P*22 MSG 0 37410.797 $GPZDA,022330.80,27,03,2024,00,00*6C EC1 1 37410.939 1.040 POS 0 37411.000 626291.673 3216635.574 QUA 0 37411.000 7 3.000 1.000 8.000 2.000 0.000 0.000 0.000 RAW 0 37411.000 4 290361.17960 1121780.82710 9.89800 22331.00000 MSG 0 37410.938 $GPGGA,022331.00,2903.611796,N,11217.808271,E,2,08,1.0,9.898,M,0.0,M,8.0,0643*76 MSG 0 37410.981 $GPVTG,46.0,T,,M,0.17,N,0.31,K,P*2A MSG 0 37411.001 $GPZDA,022331.00,27,03,2024,00,00*65 FIX 99 37411.109 48 626291.673 3216635.574 EC1 1 37411.138 1.030 POS 0 37411.200 626291.687 3216635.584 QUA 0 37411.200 7 3.000 1.000 8.000 2.000 0.000 0.000 0.000 RAW 0 37411.200 4 290361.18010 1121780.82800 9.90800 22331.20000 MSG 0 37411.137 $GPGGA,022331.20,2903.611801,N,11217.808280,E,2,08,1.0,9.908,M,0.0,M,4.0,0643*7F MSG 0 37411.180 $GPVTG,54.9,T,,M,0.21,N,0.39,K,P*2D MSG 0 37411.199 $GPZDA,022331.20,27,03,2024,00,00*67 EC1 1 37411.337 1.020 POS 0 37411.400 626291.708 3216635.595 QUA 0 37411.400 7 3.000 1.000 8.000 2.000 0.000 0.000 0.000 RAW 0 37411.400 4 290361.18070 1121780.82930 9.90400 22331.40000 MSG 0 37411.336 $GPGGA,022331.40,2903.611807,N,11217.808293,E,2,08,1.0,9.904,M,0.0,M,4.0,0643*71 MSG 0 37411.379 $GPVTG,57.9,T,,M,0.23,N,0.42,K,P*20 MSG 0 37411.398 $GPZDA,022331.40,27,03,2024,00,00*61 EC1 1 37411.538 1.030 POS 0 37411.599 626291.727 3216635.606 QUA 0 37411.599 7 3.000 1.000 8.000 2.000 0.000 0.000 0.000 RAW 0 37411.599 4 290361.18130 1121780.83050 9.90100 22331.60000 MSG 0 37411.537 $GPGGA,022331.60,2903.611813,N,11217.808305,E,2,08,1.0,9.901,M,0.0,M,4.0,0643*7D MSG 0 37411.580 $GPVTG,61.7,T,,M,0.22,N,0.41,K,P*29 MSG 0 37411.600 $GPZDA,022331.60,27,03,2024,00,00*63 EC1 1 37411.737 1.020 POS 0 37411.799 626291.750 3216635.618 QUA 0 37411.799 7 3.000 1.000 8.000 2.000 0.000 0.000 0.000 RAW 0 37411.799 4 290361.18190 1121780.83190 9.89600 22331.80000 MSG 0 37411.736 $GPGGA,022331.80,2903.611819,N,11217.808319,E,2,08,1.0,9.896,M,0.0,M,4.0,0643*7B MSG 0 37411.779 $GPVTG,64.7,T,,M,0.25,N,0.45,K,P*2F MSG 0 37411.798 $GPZDA,022331.80,27,03,2024,00,00*6D EC1 1 37411.937 1.030 POS 0 37412.000 626291.774 3216635.627 QUA 0 37412.000 7 3.000 1.000 8.000 2.000 0.000 0.000 0.000 RAW 0 37412.000 4 290361.18240 1121780.83340 9.89900 22332.00000 MSG 0 37411.937 $GPGGA,022332.00,2903.611824,N,11217.808334,E,2,08,1.0,9.899,M,0.0,M,4.0,0643*7E MSG 0 37411.980 $GPVTG,68.6,T,,M,0.25,N,0.47,K,P*20 MSG 0 37411.999 $GPZDA,022332.00,27,03,2024,00,00*66 EC1 1 37412.138 1.020 POS 0 37412.200 626291.790 3216635.646
3.1、中規(guī)中矩的雙循環(huán)
以下代碼實(shí)例中,是 Hypack RAW 數(shù)據(jù)處理中的雙循環(huán),插補(bǔ) EC1 采集數(shù)據(jù)所在定位坐標(biāo)。
數(shù)據(jù)的時(shí)間秒從小到大有序排列。
for (int j = 0; j < POSLeng; j++) { if (j == 0 && EC1Time[i] < POSTime[j])//EC1時(shí)間小于第一個(gè)POS時(shí)間 { EC1East[i] = POSEast[j] - (POSEast[j + 1] - POSEast[j]) / (POSTime[j + 1] - POSTime[j]) * (POSTime[j] - EC1Time[i]);//水深點(diǎn)東坐標(biāo) EC1North[i] = POSNorth[j] - (POSNorth[j + 1] - POSNorth[j]) / (POSTime[j + 1] - POSTime[j]) * (POSTime[j] - EC1Time[i]);//水深點(diǎn)北坐標(biāo) break; } if (j == POSLeng - 1 && EC1Time[i] > POSTime[POSLeng - 1])//EC1時(shí)間大于最后一個(gè)POS時(shí)間 { EC1East[i] = POSEast[j] + (POSEast[j] - POSEast[j - 1]) / (POSTime[j] - POSTime[j - 1]) * (EC1Time[i] - POSTime[j]);//水深點(diǎn)東坐標(biāo) EC1North[i] = POSNorth[j] + (POSNorth[j] - POSNorth[j - 1]) / (POSTime[j] - POSTime[j - 1]) * (EC1Time[i] - POSTime[j]);//水深點(diǎn)北坐標(biāo) break; } if (EC1Time[i] == POSTime[j]) { EC1East[i] = POSEast[j]; EC1North[i] = POSNorth[j]; break; } if ((EC1Time[i] > POSTime[j]) && (EC1Time[i] < POSTime[j + 1])) { EC1East[i] = POSEast[j] + (POSEast[j + 1] - POSEast[j]) / (POSTime[j + 1] - POSTime[j]) * (EC1Time[i] - POSTime[j]);//水深點(diǎn)東坐標(biāo) EC1North[i] = POSNorth[j] + (POSNorth[j + 1] - POSNorth[j]) / (POSTime[j + 1] - POSTime[j]) * (EC1Time[i] - POSTime[j]);//水深點(diǎn)北坐標(biāo) break; } } SurveyEC1[i, 0] = EC1Time[i]; SurveyEC1[i, 1] = EC1East[i]; SurveyEC1[i, 2] = EC1North[i]; SurveyEC1[i, 3] = EC1WaterDepth[i];
以上代碼循環(huán)效率不高,測(cè)試中,當(dāng) RAW 文件 3119 KB,EC1 數(shù)據(jù)量達(dá)到 97981 個(gè),POS數(shù)據(jù)量達(dá)到 6142 個(gè),F(xiàn)IX數(shù)據(jù)量達(dá)到 503個(gè)。插補(bǔ) EC1 采集點(diǎn)的坐標(biāo)和 從 EC1 采集點(diǎn)檢索 FIX 采集的水深,很耗時(shí),達(dá)到 2 千毫秒左右,插補(bǔ)數(shù)據(jù)后,還要加載到 chart 和 dataGridView 圖表控件中,加載圖標(biāo)達(dá)到 7 百毫秒左右,導(dǎo)致顯示很慢。
3.2、采用改進(jìn)二分法的雙循環(huán)
為了提高運(yùn)算速度和效率,采用改進(jìn)二分法的雙循環(huán),根據(jù)循環(huán)原則,優(yōu)化代碼結(jié)構(gòu),使用類(lèi)封裝坐標(biāo)計(jì)算循環(huán)為 InterpCoord 函數(shù),二分法循環(huán)調(diào)用它。插補(bǔ) EC1 采集點(diǎn)的坐標(biāo)和 FIX 采集的水深,整體循環(huán)減小到 764 毫秒左右。
//根據(jù) POS 定位數(shù)據(jù)和時(shí)間數(shù)據(jù),以航速計(jì)算插補(bǔ) EC1 水深的定位坐標(biāo) //改進(jìn)二分法,加快循環(huán) int EC1Leng = ListEc1Time.Length;//EC1數(shù)據(jù)個(gè)數(shù) int MedianNum = 0; if ((EC1Leng & 1) == 0) { MedianNum = EC1Leng / 2;//偶數(shù),數(shù)據(jù)半數(shù) } else { MedianNum = (int)(EC1Leng / 2) + 1; //奇數(shù),數(shù)據(jù)半數(shù)+1 } for (int i = 0; i <= MedianNum; i++)//for (int i = 0; i < EC1Leng; i++) { //從時(shí)間秒最小索引 i = 0 開(kāi)始順序計(jì)算到中數(shù) InterpCoord(EC1Time[i], ref EC1East[i], ref EC1North[i], POSTime, POSEast, POSNorth); SurveyEC1[i, 0] = EC1Time[i]; SurveyEC1[i, 1] = EC1East[i]; SurveyEC1[i, 2] = EC1North[i]; SurveyEC1[i, 3] = EC1WaterDepth[i]; //從時(shí)間秒最大索引 i = EC1Leng - 1 開(kāi)始逆序計(jì)算到中數(shù) int ReverseOrderNum = EC1Leng - i - 1; InterpCoord(EC1Time[ReverseOrderNum], ref EC1East[ReverseOrderNum], ref EC1North[ReverseOrderNum], POSTime, POSEast, POSNorth); //組合為二維 EC1 數(shù)據(jù) SurveyEC1[ReverseOrderNum, 0] = EC1Time[ReverseOrderNum]; SurveyEC1[ReverseOrderNum, 1] = EC1East[ReverseOrderNum]; SurveyEC1[ReverseOrderNum, 2] = EC1North[ReverseOrderNum]; SurveyEC1[ReverseOrderNum, 3] = EC1WaterDepth[ReverseOrderNum]; }
使用類(lèi)封裝坐標(biāo)計(jì)算循環(huán)為 InterpCoord 函數(shù),以便構(gòu)造引用:
public class Hypack { /// <summary>計(jì)算 EC1 時(shí)間點(diǎn)的坐標(biāo)</summary> /// <param name="InterpTime">EC1時(shí)間點(diǎn)</param> /// <param name="InterpEast">EC1東坐標(biāo)</param> /// <param name="InterpNorth">EC1西坐標(biāo)</param> /// <param name="LineTime">POS時(shí)間點(diǎn)</param> /// <param name="LineEast">POS東坐標(biāo)</param> /// <param name="LineNorth">POS西坐標(biāo)</param> public static void InterpCoord(double InterpTime, ref double InterpEast, ref double InterpNorth, double[] LineTime, double[] LineEast, double[] LineNorth) { int LineLeng = LineTime.Length; if (InterpTime < LineTime[0])//EC1時(shí)間小于第一個(gè) POS 線上時(shí)間,計(jì)算EC1時(shí)間對(duì)應(yīng)坐標(biāo) { InterpEast = LineEast[0] - (LineEast[1] - LineEast[0]) / (LineTime[1] - LineTime[0]) * (LineTime[0] - InterpTime);//水深點(diǎn)東坐標(biāo) InterpNorth = LineNorth[0] - (LineNorth[1] - LineNorth[0]) / (LineTime[1] - LineTime[0]) * (LineTime[0] - InterpTime);//水深點(diǎn)北坐標(biāo) } else if (InterpTime > LineTime[LineLeng - 1])//EC1時(shí)間大于最后一個(gè) POS 線上時(shí)間,計(jì)算EC1時(shí)間對(duì)應(yīng)坐標(biāo) { InterpEast = LineEast[LineLeng - 1] + (LineEast[LineLeng - 1] - LineEast[LineLeng - 2]) / (LineTime[LineLeng - 1] - LineTime[LineLeng - 2]) * (InterpTime - LineTime[LineLeng - 1]);//水深點(diǎn)東坐標(biāo) InterpNorth = LineNorth[LineLeng - 1] + (LineNorth[LineLeng - 1] - LineNorth[LineLeng - 2]) / (LineTime[LineLeng - 1] - LineTime[LineLeng - 2]) * (InterpTime - LineTime[LineLeng - 1]);//水深點(diǎn)北坐標(biāo) } else { for (int j = 0; j < LineLeng; j++) { if (InterpTime == LineTime[j])//EC1時(shí)間等于 POS 線上時(shí)間,坐標(biāo)一致 { InterpEast = LineEast[j]; InterpNorth = LineNorth[j]; break; } if ((InterpTime > LineTime[j]) && (InterpTime < LineTime[j + 1]))//EC1時(shí)間在 POS 線上 2 個(gè)時(shí)間之間,計(jì)算EC1時(shí)間對(duì)應(yīng)坐標(biāo) { InterpEast = LineEast[j] + (LineEast[j + 1] - LineEast[j]) / (LineTime[j + 1] - LineTime[j]) * (InterpTime - LineTime[j]);//水深點(diǎn)東坐標(biāo) InterpNorth = LineNorth[j] + (LineNorth[j + 1] - LineNorth[j]) / (LineTime[j + 1] - LineTime[j]) * (InterpTime - LineTime[j]);//水深點(diǎn)北坐標(biāo) break; } } } // 嘗試如下代碼更耗時(shí),相當(dāng)于增加了循環(huán),盡管代碼簡(jiǎn)潔 找到大于目標(biāo)的第一個(gè)元素的索引 //int indexGreaterThan = Array.FindIndex(LineTime, n => n > InterpTime); 找到等于于target的第一個(gè)元素的索引 //int indexEqualThan = Array.FindIndex(LineTime, n => n == InterpTime); 找到小于target的第一個(gè)元素的索引 //int indexLessThan = Array.FindLastIndex(LineTime, n => n < InterpTime); //if (indexEqualThan >= 0) //{ // InterpEast = LineEast[indexEqualThan]; // InterpNorth = LineNorth[indexEqualThan]; //} //if (indexLessThan >= 0 && indexGreaterThan >= 0) //{ // InterpEast = LineEast[indexLessThan] + (LineEast[indexGreaterThan] - LineEast[indexLessThan]) / (LineTime[indexGreaterThan] - LineTime[indexLessThan]) * (InterpTime - LineTime[indexLessThan]);//水深點(diǎn)東坐標(biāo) // InterpNorth = LineNorth[indexLessThan] + (LineNorth[indexGreaterThan] - LineNorth[indexLessThan]) / (LineTime[indexGreaterThan] - LineTime[indexLessThan]) * (InterpTime - LineTime[indexLessThan]);//水深點(diǎn)北坐標(biāo) //} } }
3.3 、采用并行循環(huán)
為了提高到更快的運(yùn)算速度和效率,采用并行循環(huán),優(yōu)化代碼結(jié)構(gòu),調(diào)用類(lèi)封裝的坐標(biāo)計(jì)算循環(huán)為 InterpCoord 函數(shù)。插補(bǔ) EC1 采集點(diǎn)的坐標(biāo)和 FIX 采集的水深,整體循環(huán)減小到 377 毫秒左右。
Parallel.For(0, EC1Leng, j => { InterpCoord(EC1Time[j], ref EC1East[j], ref EC1North[j], POSTime, POSEast, POSNorth); SurveyEC1[j, 0] = EC1Time[j]; SurveyEC1[j, 1] = EC1East[j]; SurveyEC1[j, 2] = EC1North[j]; SurveyEC1[j, 3] = EC1WaterDepth[j]; });
四、雙循環(huán)更好的辦法
多線程處理不當(dāng)容易內(nèi)存溢出,線程間的錯(cuò)誤處理和同步問(wèn)題。需要嚴(yán)謹(jǐn)?shù)谋苊舛鄠€(gè)線程同時(shí)訪問(wèn)同一資源,否則導(dǎo)致沖突或錯(cuò)誤。存在內(nèi)存銷(xiāo)毀消耗,處理不當(dāng)反而浪費(fèi)時(shí)間,增加開(kāi)銷(xiāo)。其它方法還在探索中…
以上就是加快C#雙循環(huán)的速度效率的方法的詳細(xì)內(nèi)容,更多關(guān)于C#雙循環(huán)速度的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
C#判斷一個(gè)類(lèi)是否實(shí)現(xiàn)了某個(gè)接口3種實(shí)現(xiàn)方法
這篇文章主要介紹了C#判斷一個(gè)類(lèi)是否實(shí)現(xiàn)了某個(gè)接口3種實(shí)現(xiàn)方法,本文直接給出實(shí)現(xiàn)代碼,需要的朋友可以參考下2015-06-06C#使用偽隨機(jī)數(shù)實(shí)現(xiàn)加密用戶密碼的方法
這篇文章主要介紹了C#使用偽隨機(jī)數(shù)實(shí)現(xiàn)加密用戶密碼的方法,對(duì)于開(kāi)發(fā)C#會(huì)員系統(tǒng)或者程序安全問(wèn)題都有一定的參考借鑒價(jià)值,需要的朋友可以參考下2014-07-07C# MeasureString測(cè)量字符串函數(shù)的使用方法
這篇文章主要介紹了C# MeasureString測(cè)量字符串函數(shù)的使用方法,需要的朋友可以參考下2014-10-10淺談Async和Await如何簡(jiǎn)化異步編程(幾個(gè)實(shí)例讓你徹底明白)
本篇文章主要介紹了淺談Async和Await如何簡(jiǎn)化異步編程,小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2016-12-12C#中的Image控件用法詳解與實(shí)際應(yīng)用示例
在C#應(yīng)用程序開(kāi)發(fā)中,圖像顯示是一個(gè)常見(jiàn)的需求,無(wú)論是創(chuàng)建圖形界面還是處理圖像數(shù)據(jù),System.Windows.Controls.Image控件都是實(shí)現(xiàn)這一目標(biāo)的重要工具,本文將詳細(xì)介紹Image控件的功能、用法、優(yōu)化技巧以及一些實(shí)際應(yīng)用示例,需要的朋友可以參考下2024-06-06讀寫(xiě)XML文件的內(nèi)容并將其顯示在ListView控件上的方法
下面小編就為大家?guī)?lái)一篇讀寫(xiě)XML文件的內(nèi)容并將其顯示在ListView控件上的方法。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2017-02-02C#使用Jquery zTree實(shí)現(xiàn)樹(shù)狀結(jié)構(gòu)顯示 異步數(shù)據(jù)加載
這篇文章主要為大家詳細(xì)介紹了C#使用Jquery zTree實(shí)現(xiàn)樹(shù)狀結(jié)構(gòu)顯示和異步數(shù)據(jù)加載,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2016-12-12