在上一篇「前端處理JSON資料 - 轉為陣列以及簡單篩選」說明了如何使用 $.grep() 方法在前端程式中去篩選陣列中的資料,
但是如果要處理的篩選條件是比較複雜時,使用 $.grep() 依然是可行,但總會任人覺得不是那麼方便,
尤其是寫 C# 的開發者在 .NET Framework 3.5 之後對於集合資料的操作已經熟悉並且習慣了 LINQ 語法,
而在前端程式中卻沒有這樣方便的處理方式,在處理集合資料時就會覺得綁手綁腳的,
其實這情形早已經有人做了一個解決方案,「LINQ to JavaScript」( 簡稱為 JSLINQ ),
在2009年的時候在MSDN學習園地的CodePlex教學中就有對這個函式庫做介紹「LINQ to JavaScript: 在 JavsScript 也可以用 LINQ」
接下來就來說明一下使用的方式。
LINQ to JavaScript (JSLINQ)
網址:http://jslinq.codeplex.com/
下載:http://jslinq.codeplex.com/releases/view/28886
目前的版本是 v2.10 , 2009年6月16日發佈
下載「JSLINQ_v2.10_SourcePlusExamples.zip」檔案並解壓縮,
如果想要馬上了解JSLINQ有什麼樣的功能以及可以做到什麼樣的操作,可以馬上看「Samples.htm」
針對JSLINQ裡面每一種方法的操作做詳盡的說明,而JSLINQ也有提供完整的Sample Unit Tests「TestSamples.htm」
而最重要的就是JSLINQ的函式庫本身,在「scripts」目錄中有三個檔案:JSLINQ.js, JSLINQ-vsdoc.js, Samples.js
其中Samples.js就是Sample的前端程式,包含了範例資料以及執行程式本身還有單元測試的程式,
我覺得這個Samples.js相當重要,因為裡面有相當詳盡的程式操作方法,甚至是前端程式的單元測試寫法可以作為參考,
如果說當使用JSLINQ遇到問題時,可以開啟 Samples.js 來查閱程式內容,就應該可以略知一二。
而「JSLINQ.js」就是函式庫本身,這是最重要的檔案,而使用上只要將檔案加入到專案並且include之後就可以使用,
「JSLINQ-vsdoc.js」這個檔案對於使用Visual Studio進行開發的程式人員也是相當重要,
因為只要在在網頁中或是檔案中參照這個檔案,在Visual Studio裡面出現智能顯示 ,
ASP.NET MVC 3 Razor ViewPage中加入 vsdoc的方式
獨立的JS檔案中加入 vsdoc 的方式
這邊提供一個簡單的方式在獨立JS檔案快速加入reference的方法,
首先在方案總管中選定你要加入參考的JS檔案
選定之後,按住滑鼠的左鍵不放,並且直接拖曳到已開啟的JS檔案裡,然後放開,就會自動加入一段reference的語法
PS.
記得在加入參考之後一定要更新 JScript Intellisense,更新的快捷鍵是「CTRL + SHIFT + J」如此才能正確顯示Intellisense。
如何使用並顯示JSLINQ的Intellisense
這地方要特別說明一下,不然很多人一定會發生跟我一樣的狀況,就是語法使用都正確,但怎麼試就是無法顯示Intellisense,
原本JSLINQ的操作方式
假如要接著繼續使用JSLINQ的方法,卻無法顯示Intellisense…
而在Readme.txt文件檔案中也說到,除了原本建立instance的方法:
var option1 = JSLINQ(myArray);
也另外提供了另一組建立instance的方法:
var option2 = new JSLINQ(myArray);
所以我們就用另外的建立instance的方式,
並且接著看看會不會顯示JSLINQ的Intellisense…
Done!可以正常顯示JSLINQ的Intellesense啦!這樣就方便我們編寫使用JSLINQ的前端程式了…
JSLINQ有哪些方法
我們在Visual Studio中透過Javascript Parser來看看JSLINQ有提供哪些方法,
JSLINQ提供了19個方法(從Where開始一直到最後的LastOrDefault),這些基本的方法就如同在.NET中使用LINQ是一樣的。
使用 JSLINQ
接下來我們直接使用JSLINQ Sample中的測試資料來做個簡單操作,
情境一:我們要取出FirstName是「Chris」的資料
$(document).ready(function ()
{
var result = "";
var test = new JSLINQ(Samples.People)
.Where(function (item) { return item.FirstName == "Chris"; })
.Select(function (item) { result += item.ID + "|" + item.FirstName + " " + item.LastName + "<br/>"; });
$('#ResultContent').html(result);
});
執行結果:
情境二:取出FirstName中有包含「s」或「S」的資料(記住!大小有區分喔)
$(document).ready(function ()
{
var result = "";
var test = new JSLINQ(Samples.People)
.Where(function (item)
{
return item.FirstName.indexOf("S") >= 0 || item.FirstName.indexOf("s") >= 0
})
.Select(function (item) { result += item.ID + "|" + item.FirstName + " " + item.LastName + "<br/>"; });
$('#ResultContent').html(result);
});
執行結果:
情境三:取出BookIDs中含有「1001」的資料(這個就比較進階,集合中再去對資料內的集合進行篩選)
$(document).ready(function ()
{
var result = "";
var test = new JSLINQ(Samples.People)
.Where(function (item)
{
return new JSLINQ(item.BookIDs).Count(function (inner) { return inner == 1001 }) > 0
})
.Select(function (item) { result += item.ID + "|" + item.FirstName + " " + item.LastName + "|" + item.BookIDs + "<br/>"; });
$('#ResultContent').html(result);
});
執行結果:
基本的情境說明就到此為止,如果要詳加了解JSLINQ各個方法的操作可以仔細研究 Sample.htm 以及 Sample.js並且多做練習,相信就會對JSLINQ輕鬆上手。
JSON資料轉陣列後使用JSLINQ進行操作
延續上一篇「前端處理JSON資料 - 轉為陣列以及簡單篩選」的資料來做演練,使用JSLINQ來做資料的篩選
原始取得的資料:
假定我們要取得CategoryID是「1」的Product出來,使用JSLINQ的寫法如下:
function UseJSLinq()
{
var result = GetData(ActionUrls.GetProducts);
var details = "<hr/>";
var currentData = JSLINQ(result)
.Where(function(item) { return item.CategoryID == "1"; })
.Select(function(item)
{
details += item.ProductID + "|" + item.ProductName + "|" + item.CategoryID + "|" + item.CategoryName + "|"+ item.SupplierID + "|"+ item.CompanyName + "|" + "<br/>";
});
$('#Products').html(details);
}
執行的結果:
在上面的各個範例當中,我們都是最後在Select()或是Count()當中的方法進行資料的最終處理,
但如果說我們使用JSLINQ篩選後的資料還不需要馬上做最後處理(如顯示的處理),或許還要對篩選的資料再進行加工,
此時我們可以用以下的方法來操作:
function UseJSLinq2()
{
var result = GetData(ActionUrls.GetProducts);
var currentData = JSLINQ(result)
.Where(function(item) { return item.CategoryID == "1"; })
.Select(function(item){ return item;});
var details = currentData.items.length + "<hr/>";
$.each(currentData.items, function(index, item)
{
details += item.ProductID + "|" + item.ProductName + "|" + item.CategoryID + "|" + item.CategoryName + "|"+ item.SupplierID + "|"+ item.CompanyName + "|" + "<br/>";
});
$('#Products').html(details);
}
執行的結果:
一定有人覺得這兩個方法除了說多了一個Count資料外,還有什麼地方式不同的嗎?
第一個方法:
var currentData = JSLINQ(result)
.Where(function(item) { return item.CategoryID == "1"; }).Select(function(item)
{details += item.ProductID + "|" + item.ProductName + "|" + item.CategoryID + "|" + item.CategoryName + "|"+ item.SupplierID + "|"+ item.CompanyName + "|" + "<br/>";});
第二個方法:
var currentData = JSLINQ(result)
.Where(function(item) { return item.CategoryID == "1"; }).Select(function(item){ return item;});
第一個方法是直接在JSLINQ的Select()方法中把要顯示的資料給處理好,第二個方法則只是單純的將資料給返回,
但是第二個方法對於經過JSLINQ處理後返回的資料處理是有個地方需要特別提醒,
那就是不能直接對返回的資料做處理,像第二個方法所返回的資料是放在 currentData 中,
如果是直接對 currentData 做處理的話,就會有以下的結果:
用Firebug進行中斷偵錯來了解一下 currentData 裡面的情況,
這麼看就很清楚了,因為經由JSLINQ處理後所返回的資料集合,會放在 items 中,所以無法直接對 currentDate 做處理,
而是需要對 currentData.items 做處理。
所以再看一次第二個方法:
function UseJSLinq2()
{
var result = GetData(ActionUrls.GetProducts);
var currentData = JSLINQ(result)
.Where(function(item) { return item.CategoryID == "1"; })
.Select(function(item){ return item;});
var details = currentData.items.length + "<hr/>";
$.each(currentData.items, function(index, item)
{
details += item.ProductID + "|" + item.ProductName + "|" + item.CategoryID + "|" + item.CategoryName + "|"+ item.SupplierID + "|"+ item.CompanyName + "|" + "<br/>";
});
$('#Products').html(details);
}
針對 currentData.items 做處理,而不是對 currentData 本身,要特別注意這個小地方的不同。
補遺:使用ToArray()方法
發佈文章後再一次Review文章內容,然後發現到JSLINQ有提供一個方法:ToArray()
看來這應該是把JSLINQ處理後的資料中items的部份給提出,看看原始碼的內容:
果不其然……這就是我沒有仔細看原始碼的後果,天真的以為JSLINQ忘記要做這個步驟,
所以我們就可以使用ToArray()方法將JSLINQ處理後的items給取出來使用,
那前面的那一段程式碼就可以改成下面的內容:
function UseJSLinq3()
{var result = GetData(ActionUrls.GetProducts);
var currentData = new JSLINQ(result).Where(function(item) { return item.CategoryID == "1"; }).Select(function(item){ return item;}).ToArray();var details = currentData.length + "<hr/>";$.each(currentData, function(index, item)
{details += item.ProductID + "|" + item.ProductName + "|" + item.CategoryID + "|" + item.CategoryName + "|"+ item.SupplierID + "|"+ item.CompanyName + "|" + "<br/>";});$('#Products').html(details);}
而最後的執行結果就如直接拿currentData.items的執行結果是相同的:
補上並且更正原本文章內容的缺漏與錯誤。
以上就是對LINQ to JavaScript(JSLINQ)的一些簡單的說明以及操作示範,
透過JSLINQ的操作讓我們可以在開發前程式的時候繼續使用LINQ相同觀念的方式來操作集合資料。
參考連結:
MSDN CodePlex教學 - LINQ to JavaScript: 在 JavsScript 也可以用 LINQ
以上
另一款類似的LinqJs最後更新日期比較新
回覆刪除http://linqjs.codeplex.com
有關Linq.js也會在之後介紹,
回覆刪除目前的前端語言使用類似Linq語法操作,好像SQLike與linq.js這兩種比較完整