使用LINQ检索数据

Xar*_*ord 11 .net c# linq sqlite join

因为几个晚上我一直坚持这个问题.SQLite我的应用程序中有数据库.我从一个文件创建了SQLite DB.ERD图如下所示: 在此输入图像描述

现在,在我的应用程序中,我创建了与数据库的连接:

using (var conn = new SQLiteConnection(DB_PATH))
{
    // retrieving statemets...
}
Run Code Online (Sandbox Code Playgroud)

我创建了代表我的数据库中的表的类:

public class Kantory
{
        public Kantory()
        {
            this.kursy = new HashSet<Kursy>();
        }

        [SQLite.PrimaryKey, SQLite.AutoIncrement]
        public int id_kantory { get; set; }
        public string nazwa { get; set; }

        public virtual ICollection<Kursy> kursy { get; set; }
}

public class Waluty
{
        public Waluty()
        {
            this.kursy = new HashSet<Kursy>();
        }

        [SQLite.PrimaryKey, SQLite.AutoIncrement]
        public int id_waluty { get; set; }
        public string nazwa { get; set; }

        public virtual ICollection<Kursy> kursy { get; set; }
}

public class Kursy
{
        [SQLite.PrimaryKey, SQLite.AutoIncrement]
        public int id_kursy { get; set; }
        public int id_kantory { get; set; }
        public int id_waluty { get; set; }
        public decimal kurs { get; set; }
        public System.DateTime data { get; set; }
        public int aktualne { get; set; }

        public virtual Kantory kantory { get; set; }
        public virtual Waluty waluty { get; set; }
}
Run Code Online (Sandbox Code Playgroud)

如你所见,在kursy表格中我有两个外键 - id_kantoryid_waluty.

现在非常好奇和奇怪的事情发生了.当我尝试使用带有INNER JOIN语句的普通SQL状态检索来检索某些信息时- 它工作正常!:

using (var conn = new SQLiteConnection(DB_PATH))
{
    var query = new SQLiteCommand(conn);
    query.CommandText = "SELECT * FROM Kursy INNER JOIN Kantory ON Kursy.id_kursy=Kantory.id_kantory WHERE Kantory.id_kantory = 1";
    var result = query.ExecuteQuery<Kursy>();
}
Run Code Online (Sandbox Code Playgroud)

这段代码工作正常!但是当我尝试使用LINQ这样的类时:

using (var conn = new SQLiteConnection(DB_PATH))
{
    var result = conn.Table<Kursy>().Where(k => k.kantory.id_kantory == 1).FirstOrDefault();
}
Run Code Online (Sandbox Code Playgroud)

它抛出了一个NotSupportedException!消息是:成员访问无法编译表达式

但是,当我使用LINQ而没有加入另一个类时,我使用我的类它可以工作!:

using (var conn = new SQLiteConnection(DB_PATH))
{
        var result = conn.Table<Kursy>().Where(k => k.id_kursy == 1).FirstOrDefault();
}
Run Code Online (Sandbox Code Playgroud)

所以最后:我的问题是我无法使用LINQ查询加入更多的那个表.似乎这个模型在课堂上是错误的,但我真的不知道为什么......

PS.这是Windows Phone 8.1应用程序,因此我无法使用Entity Framework.

Sha*_*tin 11

这是有效的代码.它仅使用EntityFramework 6.3.1而不使用任何SQLite特定程序集.

我明白你不想使用实体框架.要想为此添加答案,我们需要知道SQLite您正在使用的具体程序集.例如,你在使用DbLinq吗?

具体来说,哪些组件包含以下方法?

  • SQLiteCommand.ExecuteQuery<T>()
  • SQLiteConnection.Table<T>()

无论如何,这里是与Entity Framework一起使用的代码.

using System;
using System.Linq;
using System.Data.Entity;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;

namespace SQLite
{
    class Program
    {
        static void Main(string[] args)
        {
            using (var conn = new SQLiteConnection(@"C:\linqToSqlite.db"))
            {
                SeedEntities(conn);

                // this is the query that DID work for you
                var result1 = conn.Kursy
                    .Where(k => k.id_kursy == 1)
                    .FirstOrDefault();

                Console.WriteLine(
                    string.Format("id_kursy:{0}", result1.id_kursy));

                // this is the query that did NOT work for you
                // it does work here
                var result2 = conn.Kursy
                    .Where(k => k.kantory.id_kantory == 1)
                    .FirstOrDefault();

                Console.WriteLine(
                    string.Format("id_kursy:{0}", result2.id_kantory));
            }

            Console.ReadKey();
        }

        private static void SeedEntities(SQLiteConnection conn)
        {
            SeedEntities(conn);
            // make sure two entities exist with the appropriate ids
            if (!conn.Kantory.Any(x => x.id_kantory == 1))
            {
                conn.Kantory
                    .Add(new Kantory() { id_kantory = 1 });
            }

            if (!conn.Kursy.Any(x => x.id_kantory == 1))
            {
                conn.Kursy
                    .Add(new Kursy() { id_kantory = 1 });
            }

            conn.SaveChanges();
        }        
    }

    public class SQLiteConnection : DbContext
    {
        public SQLiteConnection(string connString) : 
            base(connString) {}
        public DbSet<Kantory> Kantory { get; set; }
        public DbSet<Kursy> Kursy { get; set; }
    }

    public class Kantory
    {
        public Kantory()
        {
            this.kursy = new HashSet<Kursy>();
        }

        [Key]
        public int id_kantory { get; set; }
        public virtual ICollection<Kursy> kursy { get; set; }
    }

    public class Kursy
    {
        [Key]
        public int id_kursy { get; set; }
        public int id_kantory { get; set; }
        public virtual Kantory kantory { get; set; }
    }
}
Run Code Online (Sandbox Code Playgroud)

我担心我使用了与你不同的技术,因为我不知道你使用的确切装配.例如,不清楚您用于该Table<T>()方法的程序集.所以,我使用的DbContext.Kursy方法代替以下参考:

  • EntityFramework.dll
  • EntityFramework.SqlServer.dll
  • System.dll
  • System.ComponentModel.DataAnnotations.dll

换句话说,它仅适用于EntityFramework 6.1.3,不需要任何SQLite特定的程序集.

对于与您的需求相关的答案,SQLite您引用了哪些具体参考?