2

linqは初めてです。左結合データベースクエリ(PostGIS)からLINQを使用してオブジェクトをロードするにはどうすればよいですか?

これは私のデータベースクエリです:

SELECT          
                dt.id, 
                dt.type, 
                dta.id as "AttId",
                dta.label,
                dtav.id as "AttValueId",
                dtav.value

FROM            public."dataTypes" dt, 
                public."dataTypeAttributes" dta
LEFT JOIN       public."dataTypeAttributeValues" dtav
ON              dta.id = "dataTypeAttributeId"        
WHERE           dt.id = dta."dataTypeId"
ORDER BY        dt.type, dta.label, dtav.value

そして、ここに出力例があります:

ここに画像の説明を入力してください

私は3つのエンティティを持っています:

public class TypeData
{
    public int ID { get; set; }
    public string Type { get; set; }
    public TypeDataAttribute[] Attributes { get; set; }

}
public class TypeDataAttribute
{
    public int ID { get; set; }
    public string Label { get; set; }
    public TypeDataAttributeValue[] Values { get; set; }
}

public class TypeDataAttributeValue
{
    public int ID { get; set; }
    public string Value { get; set; }
}

アップデート

これが私が立ち往生しているところです:

...
using (NpgsqlDataReader reader = command.ExecuteReader())
{

    if (reader.HasRows)
    {
        IEnumerable<TypeData> typeData = reader.Cast<System.Data.Common.DbDataRecord>()
            .GroupJoin( //<--stuck here.
    }
...

解決:

AmyBの答えを使用して、これは私のオブジェクトを埋めたものです:

using (NpgsqlDataReader reader = command.ExecuteReader())
{

    if (reader.HasRows)
    {

        var groups = reader.Cast<System.Data.Common.DbDataRecord>()
            .GroupBy(dr => new { ID = (int)dr["id"], AttID = (int)dr["AttId"] })
            .GroupBy(g => g.Key.ID);

        typeDataList = (
            from typeGroup in groups
            let typeRow = typeGroup.First().First()
            select new TypeData()
            {
                ID = (int) typeRow["id"],
                Type = (string) typeRow["type"],
                Attributes = 
                (
                    from attGroup in typeGroup
                    let attRow = attGroup.First()
                    select new TypeDataAttribute()
                    {
                        ID = (int)attRow["AttId"],
                        Label = (string)attRow["label"],
                        PossibleValues =
                        (
                            from row in attGroup
                            where !DBNull.Value.Equals(attRow["AttValueId"])
                            select new TypeDataAttributeValue() { ID = (int)row["AttValueId"], Value = (string)row["value"] }
                        ).ToArray()
                    }
                ).ToArray()
            }
        );
    }
}
4

4 に答える 4

2

つまり、私が正しく理解していれば、満足のいくデータベースクエリがありますが、行と列の形をした結果を取得して、階層的な形の結果に投影したいとします。


結果がList<Row>

public class Row
{
  public int id {get;set;}
  public string type {get;set;}
  public int attid {get;set;}
  public string label {get;set;}
  public int? attvalueid {get;set;}
  public string value {get;set;}
}

次に、2回グループ化し、各最上位グループをにType、各子レベルグループをに、Attribute各行をに変換しますValue(行が空の値でない場合)。

List<Row> queryResult = GetQueryResult();

//make our hierarchies.
var groups = queryResult
  .GroupBy(row => new {row.id, row.attid})
  .GroupBy(g => g.Key.id);

//now shape each level
List<Type> answer =
(
  from typeGroup in groups
  let typeRow = typeGroup.First().First()
  select new Type()
  {
    id = typeRow.id,
    type = typeRow.type,
    Attributes =
    (
      from attGroup in typeGroup
      let attRow = attGroup.First()
      select new Attribute()
      {
        id = attRow.attid,
        label = attRow.label
        Values =
        (
          from row in attRow
          where row.attvalueid.HasValue  //if no values, then we get an empty array
          select new Value() {id = row.attvalueid, value = row.value }
        ).ToArray()
      }
    ).ToArray()
  }
).ToList();
于 2012-09-19T19:46:09.693 に答える
1

GroupJoinsytnaxをお試しください

Join通常の内部結合の構文もあります

このリンクには、グループ参加の例があります

于 2012-09-19T17:36:21.737 に答える
1
 var q = (from dt in public."dataTypes"
         // Join the second table to the first, using the IDs of the two tables <-- You may join on different columns from the two tables
         join dta in public."dataTypeAttributes" on
         new { ID = dt.id } equals
         new { ID = dta.id }
         // Join the third table to the first, using the IDs of the two tables
         join dtav in public."dataTypeAttributeId" on
         new { ID = dt.id } equals
         new { ID = dtav.id }
         // Conditional statement
         where dt.id == dta."dataTypeId"
         // Order the results
         orderby dt.type, dta.label, dtav.value
         // Select the values into a new object (datObj is a created class with the below variables)
         select new datObj() {
            ID = dt.id,
            Type = dt.type,
            AttID = dta.id,
            Label = dta.label,
            AttValueID = dtav.id,
            AttValue = dtav.value
         }).ToList()

whereこれにより、ステートメントで指定された順序で、ステートメントに一致するリストが返されますorderby

正確にはあなたが必要としていることではありませんが、あなたがしなければならないことの例をあなたに与えるべきです。

于 2012-09-19T18:03:22.980 に答える
0

Yopuはこれをチェックする必要があります:http://codingsense.wordpress.com/2009/03/08/left-join-right-join-using-linq/

于 2012-09-19T14:26:45.990 に答える