SQLCompiler for LINQ(VB) のサンプル (LINQPad 用 LINQ to Entities 基本サンプル ) 本サンプルで使用した Visual Studio プロジェクトの pubs データベースの概念モデルは 以下のテーブル名とカラム名が 直接 SQL Sever へクエリする場合と異なるので が補正されています テーブル名が異なるもの employee employees royshed roysheds titleauthor titleauthors カラム名が異なるもの discounts.discount discounts.discount1 titles.title titles.title1 Northwind データベースについては 本サンプルで使用しているテーブル名とカラム名は 概念モデルと一致しています < 一覧表 > リンク No1.linq 単一テーブルを使用する表 1 No2.linq 2 つのテーブルのクロス結合を使用する表 2 No3.linq 2 つのテーブルの内部結合を使用する表 3 No4.linq No3.linq で GROUP BY 句, ORDER BY 句, COUNT(*) を使用する表 4 No5.linq 二項演算子 (+) を使用する表 5 No6.linq 単純 CASE 式を使用する表 6 No7.linq 検索 CASE 式を使用する表 7 No8.linq 単項演算子と括弧式を使用する表 8 No9.linq 検索条件に括弧を使用する表 9 No10.linq 検索条件に NOT を使用する表 10 No11.linq 数値 ( 小数 ) リテラルを使用する表 11 No12.linq GROUP BY 句と AVG 関数を使用する表 12 No13.linq No12.linq の AVG 関数に DISTINCT を使用する表 13 No14.linq GROUP BY 句と COUNT 関数を使用する表 14 No15.linq No14.linq の COUNT 関数に DISTINCT を使用する表 15 No16.linq FROM 句でサブクエリを使用する表 16 No17.linq WHERE 句でサブクエリを使用する表 17 No17_2.linq No17.linq と等価な SQL を IN 限定子を使用して作成する表 17_2 No18.linq HAVING 句でサブクエリを使用する表 18 No19.linq 選択リストでサブクエリを使用する表 19 1
No20.linq LIKE 限定子を使用する 表 20 No21.linq No20.linq で NOT LIKE 限定子を使用する 表 21 No22.linq No21.linq の述語全体を否定する 表 22 No23.linq BETWEEN 限定子を使用する 表 23 No24.linq No23.linq で NOT BETWEEN 限定子を使用する 表 24 No25.linq No24.linq の述語全体を否定する 表 25 No26.linq IS NULL 限定子を使用する 表 26 No27.linq No26.linq で IS NOT NULL 限定子を使用する 表 27 No28.linq No27.linq の述語全体を否定する 表 28 No29.linq IN 限定子を使用する 表 29 No30.linq No29.linq で NOT IN 限定子を使用する 表 30 No31.linq No30.linq の述語全体を否定する 表 31 No32.linq EXISTS 限定子を使用する 表 32 No33.linq No32.linq を NOT EXISTS 限定子にする 表 33 No34.linq ALL 限定子を使用する 表 34 No35.linq No34.linq を NOT ALL 限定子にする 表 35 No36.linq ANY 限定子を使用する 表 36 No37.linq No36.linq で NOT ANY 限定子を使用する 表 37 No38.linq IN 限定子を使用する 表 38 No39.linq No38.linq で NOT IN 限定子を使用する 表 39 No40.linq No39.linq の述語全体を否定する 表 40 No43.linq 自己結合を使用する 表 43 No45.linq 集合演算を FROM 句で使用する 表 45 No46.linq 集合演算を WHERE 句で使用する 表 46 No46_2.linq No46.linq の WHERE 句で IN 限定子を使用する 表 46_2 No47.linq 集合演算を選択リストで使用する 表 47 No48.linq 集合演算をルートクエリで使用する 表 48 No49.linq ビット型を FROM 句で使用する 表 49 No50.linq No49.linq の 2 つ目の結合キーの左辺と右辺を入れ替える 表 50 No50_2.linq No50.linq の 2 つ目の結合キーを WHEHE 句に移動する 表 50_2 No51.linq ビット型を WHERE 句で使用する 表 51 No52.linq ビット型を選択リストで使用する 表 52 No53.linq 時間型を FROM 句で使用する 表 53 No54.linq 時間型を WHERE 句で使用する 表 54 No55_2.linq 時間型を選択リストで使用する (1) 表 55_2 No55_3.linq 時間型を選択リストで使用する (2) 表 55_3 No55_5.linq 時間型を選択リストで使用する (3) 表 55_5 2
No56_2.linq 選択リストで リレーションエイリアス.* を指定する 表 56_2 No57_2.linq 選択リストで テーブル名.* を指定する 表 57_2 No58_2.linq テーブルにエイリアスを付与しないでテーブル名を直接使用する 表 58_2 No59.linq ORDER BY 句を数値で指定する 表 59 No60.linq ORDER BY 句をカラム名で指定する (1) 表 60 No61.linq ORDER BY 句をカラム名で指定する (2) 表 61 No62.linq ORDER BY 句で選択リストに含まれないカラム名を指定する (1) 表 62 No63.linq ORDER BY 句で選択リストに含まれないカラム名を指定する (2) 表 63 No75.linq 集合演算に ORDER BY 句を使用する 表 75 No1.linq 単一テーブルを使用する SELECT TOP 10 au_lname, au_fname FROM authors WHERE au_id = '172-32-1176' authors _.Where(Function(x1) x1.au_id = "172-32-1176") _ x1.au_lname, _ x1.au_fname}) _.Take(10) No2.linq 2 つのテーブルのクロス結合を使用する SELECT t2.au_id, t1.au_lname FROM authors AS t1, titleauthors AS t2 WHERE t1.au_id = t2.au_id authors _.SelectMany(Function(t2) titleauthors, _ Function(t1, t2) New With {t1, t2}) _.Where(Function(x1) x1.t1.au_id = x1.t2.au_id) _ x1.t2.au_id, _ x1.t1.au_lname}) 3
No3.linq 2 つのテーブルの内部結合を使用する SELECT t2.au_id, t1.au_lname FROM authors AS t1 INNER JOIN titleauthors AS t2 ON t1.au_id = t2.au_id authors _ Function(t1) t1.au_id, _ Function(t2) t2.au_id, _ Function(t1, t2) New With {t1, t2}) _ x1.t2.au_id, _ x1.t1.au_lname}) LINQ コード No4.linq No3.linq で GROUP BY 句, ORDER BY 句, COUNT(*) を使用する SELECT t2.au_id, COUNT(*) FROM authors AS t1 INNER JOIN titleauthors AS t2 ON t1.au_id = t2.au_id GROUP BY t2.au_id ORDER BY t2.au_id DESC /* NotSupportedException が発生する (System.LINQ.IGrouping を System.Collection s.generic.ienumerable にキャストできません LINQ to Entities では Entity Data Model プリミティブ型のキャストのみがサポートされます ) */ authors _ Function(t1) t1.au_id, _ Function(t2) t2.au_id, _ Function(t1, t2) New With {t1, t2}) _.GroupBy(Function(x1) New With {.grkey1 = x1.t2.au_id}) _.Select(Function(g1) New With { _.au_id = g1.key.grkey1, _.root_alias_2 = g1.count()}) _.OrderByDescending(Function(t) t.au_id) No5.linq 二項演算子 (+) を使用する SELECT au_lname + '-' + au_fname AS au_name FROM authors WHERE au_id = '172-32-1176' authors _ 4
.Where(Function(x1) x1.au_id = "172-32-1176") _.au_name = x1.au_lname + "-" + x1.au_fname}) LINQ コード No6.linq 単純 CASE 式を使用する SELECT t2.au_id, CASE COUNT(*) WHEN 1 THEN 'one' WHEN 2 THEN 'two' ELSE 'over' END AS kosu FROM authors AS t1 INNER JOIN titleauthors AS t2 ON t1.au_id = t2.au_id GROUP BY t2.au_id /* NotSupportedException が発生する (System.LINQ.IGrouping を System.Collection s.generic.ienumerable にキャストできません LINQ to Entities では Entity Data Model プリミティブ型のキャストのみがサポートされます ) */ authors _ Function(t1) t1.au_id, _ Function(t2) t2.au_id, _ Function(t1, t2) New With {t1, t2}) _.GroupBy(Function(x1) New With {.grkey1 = x1.t2.au_id}) _.Select(Function(g1) New With { _.au_id = g1.key.grkey1, _.kosu = (If(g1.Count() = 1, "one", If(g1.Count() = 2, "two", "over")))}) LINQ コード No7.linq 検索 CASE 式を使用する SELECT t2.au_id, CASE WHEN COUNT(*) <= 2 THEN 'onetwo' ELSE 'over' END AS kosu FROM authors AS t1 INNER JOIN titleauthors AS t2 ON t1.au_id = t2.au_id GROUP BY t2.au_id /* NotSupportedException が発生する (System.LINQ.IGrouping を System.Collection s.generic.ienumerable にキャストできません LINQ to Entities では Entity Data Model プリミティブ型のキャストのみがサポートされます ) */ authors _ Function(t1) t1.au_id, _ Function(t2) t2.au_id, _ Function(t1, t2) New With {t1, t2}) _.GroupBy(Function(x1) New With {.grkey1 = x1.t2.au_id}) _.Select(Function(g1) New With { _.au_id = g1.key.grkey1, _.kosu = (If(g1.Count() <= 2, "onetwo", "over"))}) 5
No8.linq 単項演算子と括弧式を使用する SELECT au_id, -(au_ord + royaltyper) AS var WHERE au_id = '172-32-1176'.Where(Function(x1) x1.au_id = "172-32-1176") _ x1.au_id, _.var = -(x1.au_ord + x1.royaltyper)}) No9.linq 検索条件に括弧を使用する SELECT au_id WHERE (au_id = '172-32-1176' AND ((title_id = 'PS3333' OR title_id = 'BU1032') AND (au_ord = 1 OR au_ord = 2)) AND royaltyper = 100).Where(Function(x1) (x1.au_id = "172-32-1176" AndAlso ((x1.title_id = "PS3333 " OrElse x1.title_id = _ "BU1032") AndAlso (x1.au_ord = 1 OrElse x1.au_ord = 2)) AndAlso x1.royaltyper = _ 100)) _ x1.au_id}) No10.linq 検索条件に NOT を使用する SELECT au_id WHERE (NOT au_id = '172-32-1176' AND NOT (au_ord = 3 OR au_ord = 1) AND NOT royaltyper = 40) 6
.Where(Function(x1) (Not(x1.au_id = "172-32-1176") AndAlso Not(x1.au_ord = 3 OrElse x1.au_ord = _ 1) AndAlso Not(x1.royaltyper = 40))) _ x1.au_id}) No11.linq 数値 ( 小数 ) リテラルを使用する SELECT au_id, au_ord + 1.1 AS goukei WHERE au_id = '172-32-1176'.Where(Function(x1) x1.au_id = "172-32-1176") _ x1.au_id, _.goukei = x1.au_ord + 1.1D}) No12.linq GROUP BY 句と AVG 関数を使用する SELECT au_ord, AVG(royaltyper) AS heikin GROUP BY au_ord.groupby(function(x1) New With {.grkey1 = x1.au_ord}) _.Select(Function(g1) New With { _.au_ord = g1.key.grkey1, _.heikin = g1.average(function(x1) x1.royaltyper)}) No13.linq No12.linq の AVG 関数に DISTINCT を使用する SELECT au_ord, AVG(DISTINCT royaltyper) AS heikin GROUP BY au_ord.groupby(function(x1) New With {.grkey1 = x1.au_ord}) _.Select(Function(g1) New With { _.au_ord = g1.key.grkey1, _.heikin = g1.select(function(x1) CType(x1.royaltyper, Integer?)).Distinct 7
().Average()}) No14.linq GROUP BY 句と COUNT 関数を使用する SELECT au_ord, COUNT(au_ord) AS kosuu GROUP BY au_ord.groupby(function(x1) New With {.grkey1 = x1.au_ord}) _.Select(Function(g1) New With { _.au_ord = g1.key.grkey1, _.kosuu = g1.count(function(x1) g1.key.grkey1 IsNot Nothing)}) No15.linq No14.linq の COUNT 関数に DISTINCT を使用する SELECT au_ord, COUNT(DISTINCT royaltyper) AS kosuu GROUP by au_ord.groupby(function(x1) New With {.grkey1 = x1.au_ord}) _.Select(Function(g1) New With { _.au_ord = g1.key.grkey1, _.kosuu = g1.where(function(x1) x1.royaltyper IsNot Nothing).Select(Functi on(x1) x1.royaltyper).distinct().count()}) No16.linq FROM 句でサブクエリを使用する SELECT t2.au_id, t2.au_lname + ' ' + t2.au_fname AS namae, t1.royaltyper FROM (SELECT au_id, royaltyper WHERE royaltyper = 100) AS t1 INNER JOIN authors AS t2 ON t1.au_id = t2.au_id.where(function(x2) x2.royaltyper = 100) _.Select(Function(x2) New With { _ x2.au_id, _ x2.royaltyper}) _.Join(authors, _ 8
Function(t1) t1.au_id, _ Function(t2) t2.au_id, _ Function(t1, t2) New With {t1, t2}) _ x1.t2.au_id, _.namae = x1.t2.au_lname + " " + x1.t2.au_fname, _ x1.t1.royaltyper}) No17.linq WHERE 句でサブクエリを使用する SELECT t1.au_id AS t1 WHERE (SELECT t2.au_id FROM authors AS t2 WHERE t1.au_id = t2.au_id AND t1.royaltyper = 100) = '172-32-1176'.Where(Function(x1) authors _.Where(Function(x2) x1.au_id = x2.au_id AndAlso x1.roya ltyper = 100) _.Select(Function(x2) New With { _ x2.au_id}).any(function(t) "172-32-1176" = t.au_id)) _ x1.au_id}) No17_2.linq No17.linq と等価な SQL を IN 限定子を使用して作成する SELECT t1.au_id AS t1 WHERE '172-32-1176' IN (SELECT t2.au_id FROM authors AS t2 WHERE t1.au_id = t2.au_id AND t1.royaltyper = 100).Where(Function(x1) authors _.Where(Function(x2) x1.au_id = x2.au_id AndAlso x1.roya ltyper = 100) _.Select(Function(x2) New With { _ x2.au_id}).any(function(t) "172-32-1176" = t.au_id)) _ x1.au_id}) 9
LINQ コード No18.linq HAVING 句でサブクエリを使用する SELECT stor_id GROUP BY stor_id HAVING AVG(qty) > (SELECT AVG(qty) WHERE payterms = 'Net 30' GROUP BY payterms) /* LINQ to Entities では SingleOrDefault() は使用できないので FirstOrDefault() を使用する */ sales _.GroupBy(Function(x1) New With {.grkey1 = x1.stor_id}) _.Where(Function(g1) g1.average(function(x1) CType(x1.qty, Integer?)) > sales _.Whe re(function(x2) x2.payterms = "Net 30") _.Gro upby(function(x2) New With {.grkey2 = x2.payterms}) _.Sel ect(function(g2) g2.average(function(x2) CType(x2.qty, Integer?))).FirstOrDef ault()) _.Select(Function(g1) New With { _.stor_id = g1.key.grkey1}) LINQ コード No19.linq 選択リストでサブクエリを使用する SELECT stor_id, qty - (SELECT AVG(qty) WHERE stor_id = '7067' GROUP BY stor_id) AS diff WHERE stor_id = '7067' /* LINQ to Entities では SingleOrDefault() は使用できないので FirstOrDefault() を使用する */ sales _.Where(Function(x1) x1.stor_id = "7067") _ x1.stor_id, _.diff = x1.qty - sales _.Where(Function(x2) x2.stor_id = "7067") _.GroupBy(Function(x2) New With {.grkey1 = x2.stor_id}) _.Select(Function(g1) g1.average(function(x2) CType(x2. qty, Integer?))).FirstOrDefault()}) 10
LINQ コード No20.linq LIKE 限定子を使用する SELECT au_id, title_id WHERE title_id LIKE 'PS%' /* LINQ to Entities では System.Data.Linq.SqlClient.SqlMethods.Like() は使用できないので StartsWith() を使用する */.Where(Function(x1) (x1.title_id).startswith("ps")) _ x1.au_id, _ x1.title_id}) LINQ コード No21.linq No20.linq で NOT LIKE 限定子を使用する SELECT au_id, title_id WHERE title_id NOT LIKE 'PS%' /* LINQ to Entities では System.Data.Linq.SqlClient.SqlMethods.Like() は使用できないので StartsWith() を使用する */.Where(Function(x1) Not((x1.title_id).StartsWith("PS"))) _ x1.au_id, _ x1.title_id}) LINQ コード No22.linq No21.linq の述語全体を否定する SELECT au_id, title_id WHERE NOT title_id NOT LIKE 'PS%' /* LINQ to Entities では System.Data.Linq.SqlClient.SqlMethods.Like() は使用できないので StartsWith() を使用する */.Where(Function(x1) (x1.title_id).startswith("ps")) _ x1.au_id, _ x1.title_id}) 11
No23.linq BETWEEN 限定子を使用する SELECT au_id, royaltyper WHERE royaltyper BETWEEN 75 AND 100.Where(Function(x1) x1.royaltyper >= 75 AndAlso x1.royaltyper <= 100) _ x1.au_id, _ x1.royaltyper}) No24.linq No23.linq で NOT BETWEEN 限定子を使用する SELECT au_id, royaltyper WHERE royaltyper NOT BETWEEN 75 AND 100.Where(Function(x1) Not(x1.royaltyper >= 75 AndAlso x1.royaltyper <= 100)) _ x1.au_id, _ x1.royaltyper}) No25.linq No24.linq の述語全体を否定する SELECT au_id, royaltyper WHERE NOT royaltyper NOT BETWEEN 75 AND 100.Where(Function(x1) x1.royaltyper >= 75 AndAlso x1.royaltyper <= 100) _ x1.au_id, _ x1.royaltyper}) No26.linq IS NULL 限定子を使用する SELECT title_id 12
FROM titles WHERE price IS NULL.Where(Function(x1) x1.price Is Nothing) _ x1.title_id}) No27.linq No26.linq で IS NOT NULL 限定子を使用する SELECT title_id FROM titles WHERE price IS NOT NULL.Where(Function(x1) Not(x1.price Is Nothing)) _ x1.title_id}) No28.linq No27.linq の述語全体を否定する SELECT title_id FROM titles WHERE NOT price IS NOT NULL.Where(Function(x1) x1.price Is Nothing) _ x1.title_id}) No29.linq IN 限定子を使用する SELECT au_ord WHERE au_ord IN (2,3).Where(Function(x1) (New Integer?() {2, 3}).Contains(x1.au_ord)) _ x1.au_ord}) 13
No30.linq No29.linq で NOT IN 限定子を使用する SELECT au_ord WHERE au_ord NOT IN (2,3).Where(Function(x1) Not((New Integer?() {2, 3}).Contains(x1.au_ord))) _ x1.au_ord}) No31.linq No30.linq の述語全体を否定する SELECT au_ord WHERE NOT au_ord NOT IN (2,3).Where(Function(x1) (New Integer?() {2, 3}).Contains(x1.au_ord)) _ x1.au_ord}) No32.linq EXISTS 限定子を使用する SELECT t1.title_id FROM titles AS t1 WHERE EXISTS (SELECT * AS t2 WHERE t1.title_id = t2.title_id AND t2.au_ord = 3).Where(Function(x1) titleauthors.any(function(x2) x1.title_id = x2.title_id A ndalso x2.au_ord = 3)) _ x1.title_id}) No33.linq 14
No32.linq を NOT EXISTS 限定子にする SELECT t1.title_id FROM titles AS t1 WHERE NOT EXISTS (SELECT * AS t2 WHERE t1.title_id = t2.title_id AND t2.au_ord = 3).Where(Function(x1) Not(titleauthors.Any(Function(x2) x1.title_id = x2.title_ id AndAlso x2.au_ord = 3))) _ x1.title_id}) No34.linq ALL 限定子を使用する SELECT stor_id GROUP BY stor_id HAVING AVG(qty) >= ALL (SELECT AVG(qty) GROUP BY payterms) sales _.GroupBy(Function(x1) New With {.grkey1 = x1.stor_id}) _.Where(Function(g1) sales _.GroupBy(Function(x2) New With {.grkey2 = x2.payterms}) _.Select(Function(g2) New With { _.res1 = g2.average(function(x2) CType(x2.qty, Integ er?))}).all(function(t) g1.average(function(x1) CType(x1.qty, Integer?)) >= t. res1)) _.Select(Function(g1) New With { _.stor_id = g1.key.grkey1}) No35.linq No34.linq を NOT ALL 限定子にする SELECT stor_id GROUP BY stor_id HAVING NOT AVG(qty) >= ALL (SELECT AVG(qty) GROUP BY payterms) 15
sales _.GroupBy(Function(x1) New With {.grkey1 = x1.stor_id}) _.Where(Function(g1) Not(sales _.GroupBy(Function(x2) New With {.grkey2 = x2.payter ms}) _.Select(Function(g2) New With { _.res1 = g2.average(function(x2) CType(x2.qty, I nteger?))}).all(function(t) g1.average(function(x1) CType(x1.qty, Integer?)) >= _ t.res1))) _.Select(Function(g1) New With { _.stor_id = g1.key.grkey1}) No36.linq ANY 限定子を使用する SELECT stor_id GROUP BY stor_id HAVING AVG(qty) >= ANY (SELECT AVG(qty) GROUP BY payterms) sales _.GroupBy(Function(x1) New With {.grkey1 = x1.stor_id}) _.Where(Function(g1) sales _.GroupBy(Function(x2) New With {.grkey2 = x2.payterms}) _.Select(Function(g2) New With { _.res1 = g2.average(function(x2) CType(x2.qty, Integ er?))}).any(function(t) g1.average(function(x1) CType(x1.qty, Integer?)) >= t. res1)) _.Select(Function(g1) New With { _.stor_id = g1.key.grkey1}) No37.linq No36.linq で NOT ANY 限定子を使用する SELECT stor_id GROUP BY stor_id HAVING NOT AVG(qty) >= ANY (SELECT AVG(qty) GROUP BY payterms) sales _.GroupBy(Function(x1) New With {.grkey1 = x1.stor_id}) _.Where(Function(g1) Not(sales _ 16
.GroupBy(Function(x2) New With {.grkey2 = x2.payter ms}) _.Select(Function(g2) New With { _.res1 = g2.average(function(x2) CType(x2.qty, I nteger?))}).any(function(t) g1.average(function(x1) CType(x1.qty, Integer?)) >= _ t.res1))) _.Select(Function(g1) New With { _.stor_id = g1.key.grkey1}) No38.linq IN 限定子を使用する SELECT stor_id, qty WHERE qty IN (SELECT qty WHERE payterms = 'ON invoice') sales _.Where(Function(x1) sales _.Where(Function(x2) x2.payterms = "ON invoice") _.Select(Function(x2) New With { _ x2.qty}).any(function(t) x1.qty = t.qty)) _ x1.stor_id, _ x1.qty}) No39.linq No38.linq で NOT IN 限定子を使用する SELECT stor_id, qty WHERE qty NOT IN (SELECT qty WHERE payterms = 'ON invoice') sales _.Where(Function(x1) sales _.Where(Function(x2) x2.payterms = "ON invoice") _.Select(Function(x2) New With { _ x2.qty}).all(function(t) x1.qty <> t.qty)) _ x1.stor_id, _ x1.qty}) 17
No40.linq No39.linq の述語全体を否定する SELECT stor_id, qty WHERE NOT qty IN NOT (SELECT qty WHERE payterms = 'ON invoice') sales _.Where(Function(x1) Not(sales _.Where(Function(x2) x2.payterms = "ON invoice") _.Select(Function(x2) New With { _ x2.qty}).all(function(t) x1.qty <> t.qty))) _ x1.stor_id, _ x1.qty}) No43.linq 自己結合を使用する SELECT t1.stor_id AS store1, t2.stor_id AS store2 FROM stores AS t1, stores AS t2 WHERE t1.stor_id < t2.stor_id stores _.SelectMany(Function(t2) stores, _ Function(t1, t2) New With {t1, t2}) _.Where(Function(x1) String.Compare(x1.t1.stor_id,x1.t2.stor_id) < 0) _.store1 = x1.t1.stor_id, _.store2 = x1.t2.stor_id}) No45.linq 集合演算を FROM 句で使用する SELECT t3.au_id, t3.namae1, t3.r1 FROM (SELECT t2.au_id, t2.au_lname + ' ' + t2.au_fname AS namae1, t1.royaltyper AS r1 FROM (SELECT au_id, royaltyper WHERE royaltyper = 100 ) AS t1 INNER JOIN authors AS t2 ON t1.au_id = t2.au_id UNION SELECT t2.au_id, t2.au_lname + ' ' + t2.au_fname AS namae2, 18
t1.royaltyper AS r2 FROM (SELECT au_id, royaltyper WHERE royaltyper <> 100 ) AS t1 INNER JOIN authors AS t2 ON t1.au_id = t2.au_id ) t3 ORDER BY t3.r1.where(function(x3) x3.royaltyper = 100) _.Select(Function(x3) New With { _ x3.au_id, _ x3.royaltyper}) _.Join(authors, _ Function(t1) t1.au_id, _ Function(t2) t2.au_id, _ Function(t1, t2) New With {t1, t2}) _.Select(Function(x2) New With { _ x2.t2.au_id, _.namae1 = x2.t2.au_lname + " " + x2.t2.au_fname, _.r1 = x2.t1.royaltyper}) _.Union(.Where(Function(x5) x5.royaltyper <> 100) _.Select(Function(x5) New With { _ x5.au_id, _ x5.royaltyper}) _.Join(authors, _ Function(t1) t1.au_id, _ Function(t2) t2.au_id, _ Function(t1, t2) New With {t1, t2}) _.Select(Function(x4) New With { _ x4.t2.au_id, _.namae1 = x4.t2.au_lname + " " + x4.t2.au_fname, _.r1 = x4.t1.royaltyper})) _ x1.au_id, _ x1.namae1, _ x1.r1}) _.OrderBy(Function(t) t.r1) No46.linq 集合演算を WHERE 句で使用する SELECT t1.au_id AS t1 WHERE ( SELECT t2.au_id FROM authors AS t2 WHERE t1.au_id = t2.au_id AND t1.royaltyper = 100 19
UNION SELECT t2.au_id FROM authors AS t2 WHERE t1.au_id = t2.au_id AND t1.royaltyper <> 100 ) = '172-32-1176' LINQ コード /* NotSupportedException が発生する (System.LINQ.IQueryable を System.Collection s.generic.ienumerable にキャストできません LINQ to Entities では Entity Data Model プリミティブ型のキャストのみがサポートされます ) */.Where(Function(x1) authors _.Where(Function(x2) x1.au_id = x2.au_id AndAlso x1.roya ltyper = 100) _.Select(Function(x2) New With { _ x2.au_id}) _.Union(authors _.Where(Function(x3) x1.au_id = x3.au_id AndAls o x1.royaltyper <> 100) _.Select(Function(x3) New With { _ x3.au_id})).any(function(t) "172-32-1176" = t.au_id)) _ x1.au_id}) LINQ コード No46_2.linq No46.linq の WHERE 句で IN 限定子を使用する SELECT t1.au_id AS t1 WHERE '172-32-1176' IN ( SELECT t2.au_id FROM authors AS t2 WHERE t1.au_id = t2.au_id AND t1.royaltyper = 100 UNION SELECT t2.au_id FROM authors AS t2 WHERE t1.au_id = t2.au_id AND t1.royaltyper <> 100) /* NotSupportedException が発生する (System.LINQ.IQueryable を System.Collection s.generic.ienumerable にキャストできません LINQ to Entities では Entity Data Model プリミティブ型のキャストのみがサポートされます ) */.Where(Function(x1) authors _.Where(Function(x2) x1.au_id = x2.au_id AndAlso x1.roya ltyper = 100) _.Select(Function(x2) New With { _ x2.au_id}) _.Union(authors _.Where(Function(x3) x1.au_id = x3.au_id And 20
Also x1.royaltyper <> 100) _ 6" = t.au_id)) _ x1.au_id}).select(function(x3) New With { _ x3.au_id})).any(function(t) "172-32-117 No47.linq 集合演算を選択リストで使用する SELECT t1.au_ord, t1.royaltyper - ( SELECT AVG(royaltyper) AS t1 WHERE t1.au_ord = 1 GROUP BY t1.au_ord UNION SELECT AVG(royaltyper) AS t1 WHERE t1.au_ord = 1 GROUP BY t1.au_ord) AS diff AS t1 WHERE au_ord = 1 LINQ コード /* LINQ to Entities では SingleOrDefault() は使用できないので FirstOrDefault() を使用する */.Where(Function(x1) x1.au_ord = 1) _ x1.au_ord, _.diff = x1.royaltyper -.Where(Function(x2) x2.au_ord = 1) _.GroupBy(Function(x2) New With {.grkey1 = x2.au _ord}) _.Select(Function(g1) g1.average(function(x2) x2. royaltyper)) _.Union(.Where(Function(x3) x3.au_ord = 1) _.GroupBy(Function(x3) New With {.grkey 2 = x3.au_ord}) _.Select(Function(g2) g2.average(functi on(x3) x3.royaltyper))).firstordefault()}) No48.linq 集合演算をルートクエリで使用する SELECT au_id, title_id WHERE au_ord = 1 UNION SELECT au_id, title_id 21
WHERE au_ord <> 1.Where(Function(x1) x1.au_ord = 1) _ x1.au_id, _ x1.title_id}) _.Union(.Where(Function(x2) x2.au_ord <> 1) _.Select(Function(x2) New With { _ x2.au_id, _ x2.title_id})) No49.linq ビット型を FROM 句で使用する SELECT a.au_id, t.title_id FROM authors AS a INNER JOIN titleauthors AS t ON a.au_id = t.au_id AND a.contract = 1 authors _ Function(a) New With {a.au_id,.key1 = a.contract}, _ Function(t) New With {t.au_id,.key1 = (If(1 = 0, False, True))}, _ Function(a, t) New With {a, t}) _ x1.a.au_id, _ x1.t.title_id}) No50.linq No49.linq の 2 つ目の結合キーの左辺と右辺を入れ替える SELECT a.au_id, t.title_id FROM authors AS a INNER JOIN titleauthors AS t ON a.au_id = t.au_id AND 1 = a.contract authors _ Function(a) New With {a.au_id,.key1 = a.contract}, _ Function(t) New With {t.au_id,.key1 = (If(1 = 0, False, True))}, _ Function(a, t) New With {a, t}) _ x1.a.au_id, _ x1.t.title_id}) 22
No50_2.linq No50.linq の 2 つ目の結合キーを WHEHE 句に移動する SELECT a.au_id, t.title_id FROM authors AS a INNER JOIN titleauthors AS t ON a.au_id = t.au_id WHERE 1 = a.contract authors _ Function(a) a.au_id, _ Function(t) t.au_id, _ Function(a, t) New With {a, t}) _.Where(Function(x1) (If(1 = 0, False, True)) = x1.a.contract) _ x1.a.au_id, _ x1.t.title_id}) No51.linq ビット型を WHERE 句で使用する SELECT a.au_id, t.title_id FROM authors AS a INNER JOIN titleauthors AS t ON a.au_id = t.au_id WHERE a.contract = 1 authors _ Function(a) a.au_id, _ Function(t) t.au_id, _ Function(a, t) New With {a, t}) _.Where(Function(x1) x1.a.contract = (If(1 = 0, False, True))) _ x1.a.au_id, _ x1.t.title_id}) No52.linq ビット型を選択リストで使用する SELECT a.au_id, a.contract, t.title_id FROM authors AS a INNER JOIN titleauthors AS t ON a.au_id = t.au_id AND a.state = 'UT' 23
authors _ Function(a) New With {a.au_id,.key1 = a.state}, _ Function(t) New With {t.au_id,.key1 = "UT"}, _ Function(a, t) New With {a, t}) _ x1.a.au_id, _ x1.a.contract, _ x1.t.title_id}) LINQ コード No53.linq 時間型を FROM 句で使用する SELECT t1.title_id, t2.au_id FROM titles AS t1 INNER JOIN titleauthors AS t2 ON t1.title_id = t2.title_id AND t1.pubdate > '2000-01-01' /* LINQ to Entities では Parse メソッドは使用できないため DateTime コンストラクタを使用する */.SelectMany(Function(t2) titleauthors, _ Function(t1, t2) New With {t1, t2}) _.Where(Function(x1) x1.t1.title_id = x1.t2.title_id AndAlso x1.t1.pubdate > New DateTime(2000, 01, 01)) _ x1.t1.title_id, _ x1.t2.au_id}) LINQ コード No54.linq 時間型を WHERE 句で使用する SELECT t1.title_id, t2.au_id FROM titles AS t1 INNER JOIN titleauthors AS t2 ON t1.title_id = t2.title_id WHERE t1.pubdate > '2000-01-01' /* LINQ to Entities では Parse メソッドは使用できないため DateTime コンストラクタを使用する */ Function(t1) t1.title_id, _ Function(t2) t2.title_id, _ Function(t1, t2) New With {t1, t2}) _.Where(Function(x1) x1.t1.pubdate > New DateTime(2000, 01, 01)) _ x1.t1.title_id, _ x1.t2.au_id}) 24
No55_2.linq 時間型を選択リストで使用する (1) SELECT t1.title_id, t1.pubdate, t2.au_id FROM titles AS t1 INNER JOIN titleauthors AS t2 ON t1.title_id = t2.title_id WHERE t2.au_ord = 3 Function(t1) t1.title_id, _ Function(t2) t2.title_id, _ Function(t1, t2) New With {t1, t2}) _.Where(Function(x1) x1.t2.au_ord = 3) _ x1.t1.title_id, _ x1.t1.pubdate, _ x1.t2.au_id}) No55_3.linq 時間型を選択リストで使用する (2) SELECT t1.title_id, t1.pubdate, t2.au_id FROM titles AS t1 INNER JOIN titleauthors AS t2 ON t1.title_id = t2.title_id AND t1.royalty = t2.au_ord * 10 Function(t1) New With {t1.title_id,.key1 = t1.royalty}, _ Function(t2) New With {t2.title_id,.key1 = t2.au_ord * 10}, _ Function(t1, t2) New With {t1, t2}) _ x1.t1.title_id, _ x1.t1.pubdate, _ x1.t2.au_id}) No55_5.linq 時間型を選択リストで使用する (3) SELECT t1.title_id, t1.pubdate, t1.pubdate + 1 FROM titles AS t1 INNER JOIN titleauthors AS t2 ON t1.title_id = t2.title_id AND t1.royalty = t2.au_ord * 10 LINQ コード /* LINQ to Entities では TimeSpan.FromDays() は使用できないので 25
System.Data.Objects.SqlClient.SqlFunctions.DateAdd() を使用する */ Function(t1) New With {t1.title_id,.key1 = t1.royalty}, _ Function(t2) New With {t2.title_id,.key1 = t2.au_ord * 10}, _ Function(t1, t2) New With {t1, t2}) _ x1.t1.title_id, _ x1.t1.pubdate, _.root_alias_3 = System.Data.Objects.SqlClient.SqlFunctions.DateAdd( "day", CDbl( +1), x1.t1.pubdate)}) No56_2.linq 選択リストで リレーションエイリアス.* を指定する SELECT t.* FROM authors AS a INNER JOIN titleauthors AS t ON a.au_id = t.au_id WHERE t.au_ord = 3 authors _ Function(a) a.au_id, _ Function(t) t.au_id, _ Function(a, t) New With {a, t}) _.Where(Function(x1) x1.t.au_ord = 3) _ x1.t.au_id, _ x1.t.title_id, _ x1.t.au_ord, _ x1.t.royaltyper}) No57_2.linq 選択リストで テーブル名.* を指定する SELECT titleauthors.* FROM authors INNER JOIN titleauthors ON authors.au_id = titleauthors.au_id WHERE titleauthors.au_ord = 3 authors _ Function(a) a.au_id, _ Function(t) t.au_id, _ Function(a, t) New With {a, t}) _.Where(Function(x1) x1.t.au_ord = 3) _ x1.t.au_id, _ 26
x1.t.title_id, _ x1.t.au_ord, _ x1.t.royaltyper}) No58_2.linq テーブルにエイリアスを付与しないでテーブル名を直接使用する SELECT titleauthors.* FROM titles INNER JOIN titleauthors ON titles.title_id = titleauthors.title_id WHERE titleauthors.au_ord = 3 Function(t) t.title_id, _ Function(ti) ti.title_id, _ Function(t, ti) New With {t, ti}) _.Where(Function(x1) x1.ti.au_ord = 3) _ x1.ti.au_id, _ x1.ti.title_id, _ x1.ti.au_ord, _ x1.ti.royaltyper}) No59.linq ORDER BY 句を数値で指定する SELECT t1.title_id, t1.price, (SELECT COUNT(t2.price) FROM titles AS t2 WHERE t2.price > t1.price) + 1 AS rank FROM titles AS t1 ORDER BY 3 x1.title_id, _ x1.price, _.rank =.Where(Function(x2) x2.price > x1.price).count(function(x2) x2. price IsNot Nothing) + 1}) _.OrderBy(Function(t) t.rank) No60.linq 27
ORDER BY 句をカラム名で指定する (1) SELECT t1.title_id, t1.price, (SELECT COUNT(t2.price) FROM titles AS t2 WHERE t2.price > t1.price) + 1 AS rank FROM titles AS t1 ORDER BY t1.title_id x1.title_id, _ x1.price, _.rank =.Where(Function(x2) x2.price > x1.price).count(function(x2) x2. price IsNot Nothing) + 1}) _.OrderBy(Function(t) t.title_id) No61.linq ORDER BY 句をカラム名で指定する (2) SELECT t1.title_id, t1.price, (SELECT COUNT(t2.price) FROM titles AS t2 WHERE t2.price > t1.price) + 1 AS rank FROM titles as t1 ORDER BY title_id x1.title_id, _ x1.price, _.rank =.Where(Function(x2) x2.price > x1.price).count(function(x2) x2. price IsNot Nothing) + 1}) _.OrderBy(Function(t) t.title_id) No62.linq ORDER BY 句で選択リストに含まれないカラム名を指定する (1) SELECT t1.title_id, t1.price, (SELECT COUNT(t2.price) FROM titles AS t2 WHERE t2.price > t1.price) + 1 AS rank FROM titles AS t1 ORDER BY t1.pub_id 28
.OrderBy(Function(x1) x1.pub_id) _ x1.title_id, _ x1.price, _.rank =.Where(Function(x2) x2.price > x1.price).count(function(x2) x2. price IsNot Nothing) + 1}) No63.linq ORDER BY 句で選択リストに含まれないカラム名を指定する (2) SELECT t1.title_id, t1.price, (SELECT COUNT(t2.price) FROM titles AS t2 WHERE t2.price > t1.price) + 1 AS rank FROM titles as t1 ORDER BY pub_id.orderby(function(x1) x1.pub_id) _ x1.title_id, _ x1.price, _.rank =.Where(Function(x2) x2.price > x1.price).count(function(x2) x2. price IsNot Nothing) + 1}) No75.linq 集合演算に ORDER BY 句を使用する SELECT au_id, title_id WHERE au_ord = 1 UNION SELECT au_id, title_id WHERE au_ord <> 1 ORDER BY title_id.where(function(x1) x1.au_ord = 1) _ x1.au_id, _ x1.title_id}) _.Union(.Where(Function(x2) x2.au_ord <> 1) _ 29
.Select(Function(x2) New With { _ x2.au_id, _ x2.title_id})) _.OrderBy(Function(t) t.title_id) 30