LINQ:語言集成查詢(Language Integrated Query),是一系列標準查詢操作符的集合,這些操作符幾乎對每一種數據源的導航,過濾和執行都是提供了底層的基本查詢架構。
LINQ可查的數據源包括關係數據,XML,DataSet或內存中的數據.LINQ技術的重點是查詢表達式,因爲它描述了對數據源的具體操作。
Lambda 的一般規則如下:
Lambda 包含的參數數量必須與委託類型包含的參數數量相同。
Lambda 中的每個輸入參數必須都能夠隱式轉換爲其對應的委託參數。
Lambda 的返回值(如果有)必須能夠隱式轉換爲委託的返回類型。
查詢操作包含三部分:獲取數據源,創建查詢,執行查詢
//獲取數據源
string[] Devices= {"電視" ,"電冰箱","洗衣機","電話","微波爐"};
//創建查詢
var SelectDevices = from device in Devices
where device.StartsWith("電")
select device;
//執行查詢
foreach (string dev in SelectDevices)
{
Console.WriteLine("帶電的設備:{0}",dev);
}
查詢語法
var SelectDevices = from device in Devices
where device.StartsWith("電")
select device;
方法語法
var SelectDevices =Devices .Where ( device => device.StartsWith("電"))
1.投影操作符:將序列中的元素轉換爲一個由開發人員定義的形式的操作
Select :對單個序列或集合中的值進行投影。
string[] Devices = { "電視", "電冰箱", "洗衣機", "電話", "微波爐" };
var SelectDevices1 = from device in Devices
select device;
// var SelectDevices = Devices.Select(device=>device);
foreach (string dev in SelectDevices1)
{
Console.WriteLine(“所有的設備:{0}", dev);
}
SelectMany:將序列的每個元素投影到 IEnumerable<(Of <(T>)>) 並將結果序列合併爲一個序列。
class Devices
{
public string Name
{ get; set; }
public List<double> Price
{ get; set; }
}
static void Main()
{
Devices[] DeviceGroup = { new Devices { Name = "電視", Price =new List<double>{ 3000,2000} }, new Devices { Name = "電冰箱", Price =new List<double> { 4000,5000 }}, new Devices { Name = "洗衣機", Price =new List<double> { 1500,1000 }} };
var devices = DeviceGroup.SelectMany(device => device.Price );
foreach (var v in devices)
{
Console.WriteLine(v);
}
}
2.限制操作符:按照一定的限制,對序列進行過濾。
Where:對單個序列或集合中的值進行投影。
string[] Devices = { "電視", "電冰箱", "洗衣機", "電話", "微波爐" };
var SelectDevices = from device in Devices
where device.StartsWith("電")
select device;
//var SelectDevices = Devices.Where(device=>device.StartsWith ("電"));
foreach (string dev in SelectDevices)
{
Console.WriteLine("帶電的設備:{0}", dev);
}
3.排序操作符:按照升序和降序的方式對結果進行排序的功能。
OrderBy:將序列中的返回值按照升序的順序進行排列。
string[] Devices = { "電視", "電冰箱", "洗衣機", "電話", "微波爐" };
var SelectDevices = from device in Devices
orderby device
select device;
// var SelectDevices = Devices.OrderBy (device => device);
foreach (string dev in SelectDevices)
{
Console.WriteLine(“所有的設備(排序後):{0}", dev);
}
OrderByDescending:將序列中的返回值按照降序的順序進行排列。
string[] Devices = { "電視", "電冰箱", "洗衣機", "電話", "微波爐" };
var SelectDevices = from device in Devices
orderby device descending
select device;
// var SelectDevices = Devices.OrderByDescending(device => device);
foreach (string dev in SelectDevices)
{
Console.WriteLine(“所有的設備(倒序後):{0}", dev);
}
ThenBy:排序依據的次關鍵字。
Devices[] DeviceGroup = { new Devices { Name = "電視", Price = 10000 }, new Devices { Name = "電話", Price = 240 }, new Devices { Name = "電視", Price = 3000 } };
var devices = from device in DeviceGroup
orderby device.Name,device .Price
select device;
// var devices = DeviceGroup.AsQueryable().OrderBy(device => device.Name).ThenBy(device => device.Price);
foreach (var dev in devices)
{
Console.WriteLine("品名:{0},價格:{1}",dev.Name,dev.Price );
}
ThenByDescending:倒排序依據的次關鍵字。
Devices[] DeviceGroup = { new Devices { Name = "電視", Price = 10000 }, new Devices { Name = "電話", Price = 240 }, new Devices { Name = "電視", Price = 3000 } };
var devices = from device in DeviceGroup
orderby device.Name,device .Price descending
select device;
// var devices = DeviceGroup.AsQueryable().OrderBy(device => device.Name).ThenByDescending(device => device.Price);
foreach (var dev in devices)
{
Console.WriteLine("品名:{0},價格:{1}",dev.Name,dev.Price );
}
Reverse:反轉序列。
string[] Devices = { "電視", "電冰箱", "洗衣機", "電話", "微波爐" };
var SelectDevices = from device in Devices.Reverse()
select device;
//var SelectDevices = Devices.Select(device=>device).Reverse ();
foreach (string dev in SelectDevices)
{
Console.WriteLine("帶電的設備:{0}", dev);
}
4.聯接操作符:將兩個或多個數據源對象進行關聯或聯合。
Join:按照一定的條件,將兩個數據源關聯起來
var messages = from mes in A_Class
join sco in A_ScortSheet on mes.ID equals sco.ID
select new { mes.ID, mes.Name, sco.ChineseScort, sco.MathsScort };
//var messages=A_Class.Join (A_ScortSheet ,mess=>mess. ID ,scos =>scos.ID ,(mes,sco)=>new {mes.ID, mes.Name, sco.ChineseScort, sco.MathsScort });
GroupJoin:將主數據源中的每一個值或元素與次數據源中相應的值聯接起來。
var messages = A_Class.GroupJoin(A_ScortSheet, mes => mes.ID, sco => sco.ID, (mess, scor) => new { Mess = mess.ID, Mename = mess.Name, Scor = scor.Select(Scor => Scor) });
數據源1.GroupJoin(數據源2,變量1=>數據源1.關聯字段,變量2=>數據源碼2.關聯字段,(數據源1數據變量,數據源2數據列表變量)=>new{變量a=數據源1.字段1,變量b=數據源1.字段2,變量c=數據源2列表變量.Select(變量c=變量c)})
5.分組操作符:按照一定的值將序列中的值或元素進行分組。
GroupBy:Student[] students = new Student[] {
new Student{ClassName="A", Name="張三"},
new Student{ClassName ="B", Name ="李四"},
new Student{ClassName ="A" ,Name ="王五"},
new Student {ClassName ="B", Name ="趙六"},
new Student{ClassName ="B" ,Name ="錢七"},
new Student {ClassName ="B", Name ="孫八"}
};
var stus = (from stu in students
select stu).GroupBy(st => st.ClassName);
//var stus = students.GroupBy(st => st.ClassName);
foreach (var v in stus)
{
Console.WriteLine("{0}班學生:", v.Key);
foreach (var va in v)
{
Console.WriteLine(" 姓名:{0}", va.Name);
}
}
6.合併操作符:將兩個對象合併在一起。
Concat:
string[] Citys = new string[] { "北京","上海","東京"};
string[] Mobiles = new string[] {"諾基亞","摩托羅拉","三星" };
var Cont = Citys.Select(city => city).Concat(Mobiles.Select(mobil => mobil));
7.聚合操作符:在一系列值上執行特定的運算,並返回單個值。
Aggregate:從序列或集合中收集值。
string[] citys = {"北京","上海","東京"};
string newcity = citys.Aggregate((cityname,next)=>next+"-"+cityname);
Console.WriteLine(newcity);
8.Average:求一個數值序列的平均值。
Demo1:
double[] nums = {1.2,34.1,45.21,43.1 };
Console.WriteLine(nums.Average ());
9.Count:求一個數值序列的個數。(LongCount用法相同)
Demo1:
double[] nums = {1.2,34.1,45.21,43.1 };
Console.WriteLine(nums.Count(num=>num<10));
10.Sum:求一個數值序列的和。
Demo1:
double[] nums = {1.2,34.1,45.21,43.1 };
Console.WriteLine(nums.Where (numm=>numm>10).Sum(num=>num));
11.集合操作符:對元素的集合或序列集合進行操作,並返回一個集合。
Distinct:刪除集合中重複的值,並返回該項集合中互不相同的元素。
List<StudentSoc> list = new List<StudentSoc>();
list.Add(new StudentSoc { Name = "李四", Chinese = 94f });
list.Add(new StudentSoc { Name = "李四", Chinese = 94f });
list.Add(new StudentSoc { Name = "王五", Chinese = 92f });
StudentSoc s = new StudentSoc { Name = "趙六", Chinese = 78f };
list.Add(s);
list.Add(s);
//var quer = from stu in list
// select stu;
//foreach (var que in quer.Distinct())
//{
// Console.WriteLine(que.Name +":"+que.Chinese );
//}
var quer = list.Distinct();
foreach (var que in quer)
{
Console.WriteLine(que.Name + ":" + que.Chinese);
}
Union:將兩個集合或序列合併後返回不同的元素。
int[] nums1 = {1,2,3,3,4};
int[] nums2 = { 2, 3, 4, 5, 6 };
var newnums = nums1.Union(nums2);
foreach (var num in newnums)
{
Console.WriteLine(num);
}
Intersect:返回兩個集合的交集。
int[] nums1 = {1,2,3,3,4};
int[] nums2 = { 2, 3, 4, 5, 6 };
var newnums = nums1.Intersect(nums2);
foreach (var num in newnums)
{
Console.WriteLine(num);
}
Except:返回序列一中序列二沒有的值。
int[] nums1 = {1,2,3,3,4,7};
int[] nums2 = { 2, 3, 4, 5, 6 ,9,23};
var newnums = nums1.Except(nums2);
foreach (var num in newnums)
{
Console.WriteLine(num);
}
12.生成操作符:從現有的序列中創建新的序列。
Empty:指定類型的空集。
var s= Enumerable.Empty<string>();
Console.WriteLine(s.Count ());
Range:創建一個包含數字序列的集合。
foreach (var num in Enumerable.Range(3, 9))
{
Console.WriteLine(num);
}
Repeat:將值重複一定的次數。
foreach (var num in Enumerable.Repeat(“*****”,9))
{
Console.WriteLine(num);
}
13.轉換操作符:將輸入對象類型轉變爲序列的動作。
AsEnumerable:
int[] ArrInt = {1,2,3,4,5 };
foreach (int i in ArrInt .Where (arr=>arr>1))
{
Console.WriteLine(i);
}
foreach (int i in ArrInt.AsEnumerable().Where(arr => arr > 1))
{
Console.WriteLine(i);
}
Cast:將序列轉換成指定的類型。
直接對Array應用Select是不可以的。
ArrayList AL = new ArrayList();
AL.Add(1);
AL.Add(2);
AL.Add(3);
AL.Add(4);
IEnumerable <int> que=AL.Cast<int>().Select (arr=>arr);
foreach (int i in que)
{
Console.WriteLine(i);
}
OfType:過濾序列中的某種類型。
ArrayList AL = new ArrayList();
AL.Add(1);
AL.Add(2);
AL.Add("3");
AL.Add(4);
var que = AL.OfType<int>();
foreach (var i in que)
{
Console.WriteLine(i);
}
ToArray:從IEnumerable序列創建一個數組。
List<StudentSoc> list = new List<StudentSoc>();
list.Add(new StudentSoc { Name = "張三", Chinese = 90f });
list.Add(new StudentSoc { Name = "李四", Chinese = 94f });
list.Add(new StudentSoc { Name = "王五", Chinese = 92f });
list.Add(new StudentSoc { Name = "趙六", Chinese = 78f });
var stu1 = list.Select(stud => stud.Chinese);
var stu = list.Select(stud => stud.Chinese).ToArray();
ToDictionary:從IEnumerable序列創建一個Dictionary序列。
class StudentSoc
{
public string Name
{ get; set; }
public float Chinese
{ get; set; }
}
List<StudentSoc> list = new List<StudentSoc>();
list.Add(new StudentSoc { Name = "張三", Chinese = 90f });
list.Add(new StudentSoc { Name = "李四", Chinese = 94f });
list.Add(new StudentSoc { Name = "王五", Chinese = 92f });
list.Add(new StudentSoc { Name = "趙六", Chinese = 78f });
Dictionary<float ,StudentSoc> stu = list.ToDictionary(stud => stud.Chinese );
foreach (KeyValuePair<float,StudentSoc > item in stu)
{
Console.WriteLine(item.Key +" "+item.Value.Name +" "+item.Value .Chinese );
}
ToList:從IEnumerable序列創建一個List序列。
class StudentSoc
{
public string Name
{ get; set; }
public float Chinese
{ get; set; }
}
List<StudentSoc> list = new List<StudentSoc>();
list.Add(new StudentSoc { Name = "張三", Chinese = 90f });
list.Add(new StudentSoc { Name = "李四", Chinese = 94f });
list.Add(new StudentSoc { Name = "王五", Chinese = 92f });
list.Add(new StudentSoc { Name = "趙六", Chinese = 78f });
var stu = list.Select(lis=>lis.Chinese).ToList();
foreach (var item in stu)
{
Console.WriteLine(item );
}
ToLookup:從IEnumerable序列創建一個 Lookup序列。Lookup是主鍵的集合,其中主鍵對應着一個或多個值。
class OrderTable
{
public int OrderNum
{ get; set; }
public double Amount
{ get; set; }
}
List<OrderTable> list = new List<OrderTable>();
list.Add(new OrderTable { OrderNum = 1001, Amount = 1234.5 });
list.Add(new OrderTable { OrderNum = 1002, Amount = 2340 });
list.Add(new OrderTable { OrderNum = 1001, Amount = 3000 });
var lis = list.ToLookup(num => num.OrderNum, num => num.Amount);
foreach (var item in lis)
{
Console.WriteLine("訂單號:{0}",item.Key );
foreach (var v in item)
{
Console.WriteLine(" {0}元",v);
}
}
14.元素操作符:從一個序列返回單個特定的元素。
DefaultIfEmpty:將空集合替換爲包含默認的單個值的集合。
List<OrderTable> list = new List<OrderTable>();
list.Add(new OrderTable { OrderNum = 1001, Amount = 1234.5 });
list.Add(new OrderTable { OrderNum = 1002, Amount = 2340 });
list.Add(new OrderTable { OrderNum = 1001, Amount = 3000 });
var lis = list.Where(num => num.OrderNum == 1001);
foreach (var item in lis.DefaultIfEmpty(new OrderTable { OrderNum =0,Amount =0}))
{
Console.WriteLine("訂單價格:{0}", item.Amount);
}
ElementAt:返回集合中給定索引的元素。
List<OrderTable> list = new List<OrderTable>();
list.Add(new OrderTable { OrderNum = 1001, Amount = 1234.5 });
list.Add(new OrderTable { OrderNum = 1002, Amount = 2340 });
list.Add(new OrderTable { OrderNum = 1001, Amount = 3000 });
var value = list.Where(num => num.OrderNum == 1001).ElementAt (1);
Console.WriteLine("訂單號:{0}", value.Amount );
ElementAtOrDefault:是將ElementAt和DefaultIfEmpty。
List<OrderTable> list = new List<OrderTable>();
list.Add(new OrderTable { OrderNum = 1001, Amount = 1234.5 });
list.Add(new OrderTable { OrderNum = 1002, Amount = 2340 });
list.Add(new OrderTable { OrderNum = 1001, Amount = 3000 });
var value = list.Select (lis=>lis.OrderNum).ElementAtOrDefault(3);
Console.WriteLine("訂單號:{0}", value);
First:返回集合中的第一個元素(Last返回最後一個)。
List<OrderTable> list = new List<OrderTable>();
list.Add(new OrderTable { OrderNum = 1001, Amount = 1234.5 });
list.Add(new OrderTable { OrderNum = 1002, Amount = 2340 });
list.Add(new OrderTable { OrderNum = 1001, Amount = 3000 });
var value = list.Select (lis=>lis.OrderNum).First ();
Console.WriteLine("訂單號:{0}", value);
FirstOrDefault:返回集合中的第一個元素,如果不存在,返回默認值(LastOrDefault返回最後一個,如果不存在,返回默認值)。
List<OrderTable> list = new List<OrderTable>();
list.Add(new OrderTable { OrderNum = 1001, Amount = 1234.5 });
list.Add(new OrderTable { OrderNum = 1002, Amount = 2340 });
list.Add(new OrderTable { OrderNum = 1001, Amount = 3000 });
var value = list.Where (li=>li.OrderNum ==1003).Select(lis=>lis.OrderNum).FirstOrDefault();
Console.WriteLine("訂單號:{0}", value);
Single:從一個序列中返回單個元素,或唯一滿足某一特定條件的元素。(LastOrDefault返回最後一個,如果不存在,返回默認值)。
List<OrderTable> list = new List<OrderTable>();
list.Add(new OrderTable { OrderNum = 1001, Amount = 1234.5 });
list.Add(new OrderTable { OrderNum = 1002, Amount = 2340 });
list.Add(new OrderTable { OrderNum = 1001, Amount = 3000 });
var value = list.Where (li=>li.OrderNum ==1002).Select(lis=>lis.OrderNum).Single();
Console.WriteLine("訂單號:{0}", value);
SingleOrDefault:從一個序列中返回單個元素,或唯一滿足某一特定條件的元素。如果存在多條記錄,拋出異常。
List<OrderTable> list = new List<OrderTable>();
list.Add(new OrderTable { OrderNum = 1001, Amount = 1234.5 });
list.Add(new OrderTable { OrderNum = 1002, Amount = 2340 });
list.Add(new OrderTable { OrderNum = 1001, Amount = 3000 });
var value = list.Where (li=>li.OrderNum ==1002).Select(lis=>lis.OrderNum).SingleOrDefault();
Console.WriteLine("訂單號:{0}", value);
15.相等操作符:比較兩個序列的元素是否相同。
SequenceEqual
int[] Arr1 = { 1, 2, 3 };
int[] Arr2 = { 1, 2, 3 };
Console.WriteLine(Arr1.SequenceEqual(Arr2))
16.量詞操作符:是否存在部分或全部元素符合某個特定條件。
All:判定在集合中是否所有的值都滿足特定的條件。
int[] Arr1 = { 1, 1, 1 };
Console.WriteLine(Arr1.All (arr=>arr==1));
Any:判定在集合中是否有的值滿足特定的條件。
int[] Arr1 = { 1, 2, 3 };
Console.WriteLine(Arr1.Any (arr=>arr==1));
Contains:判定在集合中是否包含某個值。
int[] Arr1 = { 1, 2, 3 };
Console.WriteLine(Arr1.Contains(4));
17.分割操作符:將一個序列分割成兩個或多個序列。
Skip:跳過序列的前n個元素後返回所有的元素。
int[] Arr = { 1, 2, 3,4,5,6 };
foreach (int i in Arr.Skip(2))
{
Console.WriteLine(i);
}
SkipWhile:跳過不滿足條件的元素,返回餘下元素的序列。
需要注意的是,這種跳出過必需排序後才能全部跳過滿足條件的元素。
int[] Arr = { 1, 12, 3,4,15,6};
foreach (int i in Arr.OrderBy (nu=>nu).SkipWhile(arr=>arr<=10))
{
Console.WriteLine(i);
}
Take:返回序列的從開始到參數指定位置的元素。
int[] Arr = { 1, 2, 3,4,5,6 };
foreach (int i in Arr.Take(2))
{
Console.WriteLine(i);
}
TakeWhile:返回滿足條件的元素。
需要注意的是,這種返回必需排序後才能進行操作。
int[] Arr = { 1, 12, 3,4,15,6};
foreach (int i in Arr.OrderBy (ar=>ar).TakeWhile(arr=>arr<12))
{
Console.WriteLine(i);
}