遍历 LINQ-to-SQL 可查询时出现 InvalidOperationException
InvalidOperationException when iterating over LINQ-to-SQL Queryable
我正在使用 LINQ to SQL 将数据从 SQLite 数据库映射到 C# 对象。当我在 Visual Studio 项目中 运行 时一切正常,但由于某种原因我无法在 Unity 中工作。
非常简化的代码是这样的:
using System.Data.Linq;
using Mono.Data.Sqlite;
var connectionString = "Data Source=" + filePath + ";DbLinqProvider=SQLite;Version=3;";
var connection = new SqliteConnection(connectionString);
var context = new DataContext(connection);
foreach (Output output in context.GetTable<Output>())
{
UnityEngine.Debug.Log(output.ID);
}
但是在 foreach
的头部抛出一个 InvalidOperationException,说 "Operation is not valid due to the current state of the object".
- 我知道映射有效,因为它在 Visual Studio 中有效。
- 我知道数据库连接有效,因为它在使用 "normal"
DbCommand
s 时有效。
- 我对包含的 DLL 仍然有点不确定,但我再次在 VS 中使用那些 DLL(与 "built in" 相反)对其进行了测试并且它有效。在我的资产文件夹中,我有来自 Mono 安装的
System.Data.dll
、System.Data.Linq.dll
、Mono.Data.Sqlite
,以及来自 SQLite 网站的 sqlite3.dll
和 sqlite3.def
。
异常如下:
InvalidOperationException: Operation is not valid due to the current state of the object
System.Linq.Enumerable.Single[MemberInfo] (IEnumerable`1 source, System.Func`2 predicate, Fallback fallback)
System.Linq.Enumerable.Single[MemberInfo] (IEnumerable`1 source)
DbLinq.Data.Linq.Mapping.AttributedMetaAssociation..ctor (System.Reflection.MemberInfo member, System.Data.Linq.Mapping. AssociationAttribute attribute, System.Data.Linq.Mapping.MetaDataMember metaDataMember)
DbLinq.Data.Linq.Mapping.AttributedMetaType+<GetAssociations>c__Iterator5.MoveNext ()
System.Collections.Generic.List`1[System.Data.Linq.Mapping.MetaAssociation].AddEnumerable (IEnumerable`1 enumerable) (at / Users/builduser/buildslave/mono-runtime-and-classlibs/build/mcs/class/corlib/System.Collections.Generic/List.cs:128)
System.Collections.Generic.List`1[System.Data.Linq.Mapping.MetaAssociation]..ctor (IEnumerable`1 collection) (at /Users/ builduser/buildslave/mono-runtime-and-classlibs/build/mcs/class/corlib/System.Collections.Generic/List.cs:65)
System.Linq.Enumerable.ToList[MetaAssociation] (IEnumerable`1 source)
DbLinq.Data.Linq.Mapping.AttributedMetaType.get_Associations ()
System.Data.Linq.DataContext.SetEntitySetsQueries (System.Object entity)
System.Data.Linq.DataContext._GetOrRegisterEntity (System.Object entity)
System.Data.Linq.DataContext.Register (System.Object entity)
DbLinq.Data.Linq.Sugar.Implementation.QueryRunner.Select[Output] (DbLinq.Data.Linq.Sugar.SelectQuery selectQuery)
DbLinq.Data.Linq.Implementation.QueryProvider`1[Bitcoin.Output].GetEnumerator ()
System.Data.Linq.Table`1[Bitcoin.Output].GetEnumerator ()
DAO.SQLiteDAO.test (System.String filePath) (at Assets/DAO/SQLiteDAO.cs:103)
DAO.SQLiteDAO..ctor (System.String filePath) (at Assets/DAO/SQLiteDAO.cs:25)
SphereSpawner.Start () (at Assets/SphereSpawner.cs:30)
我在这里阅读了所有看起来相似的内容,但我从未在任何事情上主动使用 Single()
,所以这不可能;而且我很确定该列表也不为空。至少不应该。
请帮忙,我在这里疯了:P
所以是的,显然映射毕竟是问题所在。似乎 Mono.Data.Sqlite 需要比 System.Data.SQLite 更明确的属性,而我在后者中完美运行的解决方案在前者中却没有。
我发现:
- 所有
Association
必须指定 Name
。
IsForeignKey=true
必须在适用时设置。
- 显然,在
Association
中用作外键的 ID 不能存储在 public Column
成员中;相反,它们必须使用 Storage="privateMember"
包裹在 属性 中。最后,我将每个 Column
映射实现为 属性,只是为了确定。
我正在使用 LINQ to SQL 将数据从 SQLite 数据库映射到 C# 对象。当我在 Visual Studio 项目中 运行 时一切正常,但由于某种原因我无法在 Unity 中工作。
非常简化的代码是这样的:
using System.Data.Linq;
using Mono.Data.Sqlite;
var connectionString = "Data Source=" + filePath + ";DbLinqProvider=SQLite;Version=3;";
var connection = new SqliteConnection(connectionString);
var context = new DataContext(connection);
foreach (Output output in context.GetTable<Output>())
{
UnityEngine.Debug.Log(output.ID);
}
但是在 foreach
的头部抛出一个 InvalidOperationException,说 "Operation is not valid due to the current state of the object".
- 我知道映射有效,因为它在 Visual Studio 中有效。
- 我知道数据库连接有效,因为它在使用 "normal"
DbCommand
s 时有效。 - 我对包含的 DLL 仍然有点不确定,但我再次在 VS 中使用那些 DLL(与 "built in" 相反)对其进行了测试并且它有效。在我的资产文件夹中,我有来自 Mono 安装的
System.Data.dll
、System.Data.Linq.dll
、Mono.Data.Sqlite
,以及来自 SQLite 网站的sqlite3.dll
和sqlite3.def
。
异常如下:
InvalidOperationException: Operation is not valid due to the current state of the object
System.Linq.Enumerable.Single[MemberInfo] (IEnumerable`1 source, System.Func`2 predicate, Fallback fallback)
System.Linq.Enumerable.Single[MemberInfo] (IEnumerable`1 source)
DbLinq.Data.Linq.Mapping.AttributedMetaAssociation..ctor (System.Reflection.MemberInfo member, System.Data.Linq.Mapping. AssociationAttribute attribute, System.Data.Linq.Mapping.MetaDataMember metaDataMember)
DbLinq.Data.Linq.Mapping.AttributedMetaType+<GetAssociations>c__Iterator5.MoveNext ()
System.Collections.Generic.List`1[System.Data.Linq.Mapping.MetaAssociation].AddEnumerable (IEnumerable`1 enumerable) (at / Users/builduser/buildslave/mono-runtime-and-classlibs/build/mcs/class/corlib/System.Collections.Generic/List.cs:128)
System.Collections.Generic.List`1[System.Data.Linq.Mapping.MetaAssociation]..ctor (IEnumerable`1 collection) (at /Users/ builduser/buildslave/mono-runtime-and-classlibs/build/mcs/class/corlib/System.Collections.Generic/List.cs:65)
System.Linq.Enumerable.ToList[MetaAssociation] (IEnumerable`1 source)
DbLinq.Data.Linq.Mapping.AttributedMetaType.get_Associations ()
System.Data.Linq.DataContext.SetEntitySetsQueries (System.Object entity)
System.Data.Linq.DataContext._GetOrRegisterEntity (System.Object entity)
System.Data.Linq.DataContext.Register (System.Object entity)
DbLinq.Data.Linq.Sugar.Implementation.QueryRunner.Select[Output] (DbLinq.Data.Linq.Sugar.SelectQuery selectQuery)
DbLinq.Data.Linq.Implementation.QueryProvider`1[Bitcoin.Output].GetEnumerator ()
System.Data.Linq.Table`1[Bitcoin.Output].GetEnumerator ()
DAO.SQLiteDAO.test (System.String filePath) (at Assets/DAO/SQLiteDAO.cs:103)
DAO.SQLiteDAO..ctor (System.String filePath) (at Assets/DAO/SQLiteDAO.cs:25)
SphereSpawner.Start () (at Assets/SphereSpawner.cs:30)
我在这里阅读了所有看起来相似的内容,但我从未在任何事情上主动使用 Single()
,所以这不可能;而且我很确定该列表也不为空。至少不应该。
请帮忙,我在这里疯了:P
所以是的,显然映射毕竟是问题所在。似乎 Mono.Data.Sqlite 需要比 System.Data.SQLite 更明确的属性,而我在后者中完美运行的解决方案在前者中却没有。
我发现:
- 所有
Association
必须指定Name
。 IsForeignKey=true
必须在适用时设置。- 显然,在
Association
中用作外键的 ID 不能存储在 publicColumn
成员中;相反,它们必须使用Storage="privateMember"
包裹在 属性 中。最后,我将每个Column
映射实现为 属性,只是为了确定。