动态linq:有没有办法通过索引访问对象数据?

2024-02-18

我需要使用 Dynamic Linq 进行一些内存中过滤。 我的对象只有一个索引器:

public  object this[int index] { }

对我的数据的访问如下:对象[0],对象[1],...

所以我的查询是这样的:

// get FilterText from user at runtime
// eg. filterText can be: [0] > 100 and [1] = "wpf"
collection.AsQueryable().where(filterText);

有什么办法可以做到这一点吗?


我有一些消息要告诉你。

这实际上是可能的......但是! (是的,有一个但是)。

我假设您正在使用动态 Linq 库。然后,您必须使用“it”关键字才能指定要应用索引操作的当前对象。

但是...索引器的返回数据类型是对象,因此由于数据类型不匹配,您将无法编写 [0] > 100 和 [1] = "wpf"。

此外,即使您从 DynamicObject 派生并在运行时添加属性,这些属性也不会在运行时由处于当前状态的动态 linq 库解析。您只会得到类型 xxx 中不存在的字段或属性。

对此有多种解决方案,其中一些您可能会接受。

  • 一个丑陋的解决方案,如果你的数据类型数量有限,比如 n (其中 n

    it[0] > 100 AND it[1, "dummy"] = "wpf" //The dummy parameter allows you to specify return type.
    
  • 另一个丑陋的解决方案,Dynamic Linq 支持使用 ToString() 和 Convert 方法,因此,您可以编写 与上面相同的查询:

    Convert.ToDouble(it[0]) > 100 AND it[1].ToString() = "wpf".
    
  • 第三个丑陋的解决方案,你可以使用一个约定来包装 语句以告诉您如何转换数据的方式。为了 例如,你可以写:

    it[0] > 100 AND it{1} = "wpf"
    

    并将“it[”替换为“Convert.ToDouble(it[”等...

如果我是正确的,我认为您也不能在库中使用通用索引器。在这种情况下,Convert.ChangeType 对您没有任何好处,因为返回类型仍然是对象。

也许我或其他人会在一段时间内重写库来支持这类事情,但我在不久的将来(几周)没有时间这样做。

好吧,很抱歉,但我必须在 15 分钟内到达某个地方,所以我希望我们稍后会采取更好的解决方案!

将自己传送到会议现场

UPDATE:

我想我可能已经找到了解决您(和我)问题的方法!

在 DLINQ 库中,您可以在 IxxxSignatures 接口中添加您希望使用的类型的成员。

因此,我在 IEqualitySignatures 中添加(例如):

void F(Object x, Int32 y);

并像这样修改了 else 块中的(在本例中)ParseComparison 方法。

left = Expression.Convert(left, right.Type);

而且,不管你信不信,它确实有效:)

我没有测试所有类型的操作,因为我没有添加其他类型和操作的签名,但它应该是非常简单的!

UPDATE

更新了上面的一些小东西。

我正在对此进行更多实验,虽然它可能也不是最漂亮的解决方案,但您可以执行类似的操作(DataObject 只是带有索引器的 DynamicObject):

    [TestMethod]
    public void DynamicTest()
    {
        List<DataObject> dataObjects = new List<DataObject>();

        dynamic firstObject = new DataObject();
        dynamic secondObject = new DataObject();

        firstObject.dblProp = 10.0;
        firstObject.intProp = 8;
        firstObject.strProp = "Hello";

        secondObject.dblProp = 8.0;
        secondObject.intProp = 8;
        secondObject.strProp = "World";

        dataObjects.Add(firstObject);
        dataObjects.Add(secondObject);

        /* Notice the different types */
        string newQuery = FormatQuery("dblProp > 9.0 AND intProp = 8 AND strProp = 'Hello'");

        var result = dataObjects.Where(newQuery);

        Assert.AreEqual(result.Count(), 1);
        Assert.AreEqual(result.First(), firstObject);
    }

以及某种格式方法,例如(假设我已经编写了完整的方法):

    public string FormatQuery(string query)
    {
        query = query.Replace('\'', '\"');

        string[] operators = new string[] { "<", ">", "!=", "<=", ">=", "<>", "=" };

        string[] parts = query.Split();

        for (int i = 0; i < parts.Length; i++)
        {
            if (operators.Contains(parts[i]))
            {
                parts[i - 1] = "it[\"" + parts[i - 1] + "\"]";
            }
        }

        return String.Join(" ", parts);
    }

我们当然可以用扩展方法来代替。

或者...我们可以使用类似的方法将该方法放入 DLINQ 库中(尽管这并不是一个好主意):

if (typeof(T).GetInterface("IDynamicMetaObjectProvider", true) != null)
    whereClause = whereClause.FormatQuery();

并且,检查类型是否实现了字符串索引器,例如(忽略此处的 IndexerName 属性):

if (t.GetType().GetProperty("Item") != null)

这将使“普通用户”能够编写:

data.Where("dblProp > 9.0 AND intProp = 8 AND strProp = 'Hello'")

好吧,也许把这些东西放在那里不太好,但你明白了。你可以有! :)

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

动态linq:有没有办法通过索引访问对象数据? 的相关文章

随机推荐

  • 按下按钮时 GPIO 事件检测不给出输出

    以下 python 脚本应该等待按钮按下 打印按钮按下消息 然后退出 但是 当我按下按钮时 什么也没有打印 然后 当我按回车键时 脚本会打印 检测到按钮按下 然后停止 我如何修复此代码 以便在按下按钮时打印 检测到按钮按下 我按照教程制作了
  • 使用Guava Cache将数据持久化到硬盘

    我是番石榴缓存的新手 如何在缓存中创建以下内容 像平常一样将数据保存在内存中 当缓存的大小超过给定的数字时 它将把缓存中的数据持久保存在硬盘上的可配置文件中 这可能会有所帮助 扩展 Guava 缓存以溢出到磁盘 http www javac
  • 将参数传递给 data.table 聚合函数

    我有一个函数可以计算变量的加权平均值 并使用以下方法按时间段对其进行分组data table聚合语法 但是 我想以编程方式提供加权列的名称 有没有办法在仍然使用传统方法的情况下实现这一目标data table句法 功能wtmean1下面演示
  • 应用程序在后台被杀死时的应用程序生命周期

    关于我遇到的问题的一些背景 在我的应用程序中 我有一个单例对象 我经常使用它来访问网络调用的 id 和令牌等内容 有时 当应用程序在后台被终止时 这个单例就会失去其状态 但是 当应用程序再次打开并在某些情况下启动时Activity经过发射器
  • 执行shell命令(c)

    这部分代码指示我的程序 生成屏幕截图 生成命令并退出 关闭 自身 这可用于使用程序中的键切换到程序 例如生成 gimp 或用户想要使用的另一个图像编辑器 case SWITCH TO if arg char commandline 256
  • Android 单元测试的最佳实践?

    我正在开发一个移动安卓应用程序 Android 单元测试最常用的库 框架有哪些 我感觉大部分业务逻辑 数据库测试 Web服务测试都可以使用JUnit来完成 但是 测试 UI UI 工作流程等的最佳方法是什么 例如 我们如何测试Android
  • Mechanize 无法在 Google Appengine 中自动登录 Gmail

    我已经使用 mechanize 并在 GAE 上部署了一个应用程序 它运行良好 但是 对于我正在制作的应用程序 我正在尝试通过 mechanize 自动登录 Gmail 它在本地计算机上的开发环境以及部署在 appengine 上后都不起作
  • 重新定义后更新变量值

    一个新手问题给各位 R 朋友 案例场景 我定义变量A A 数字 我根据A定义其他变量 B number A 我改变A的定义 A 不同的数字 问 如何让 R 自动更新 B 的值 而不需要再次重新定义它 例如 1 A 1000 2 B A 10
  • 如何在android中使用相机捕获自定义尺寸的图像?

    如何在android中捕捉方形图像 我想在android中通过intent调用Camera来捕获方形图像 例如300x300像素 我该怎么做 编辑 自 API 级别 21 起已弃用 使用 Camera Size 嵌套类 http devel
  • java.io.EOFException 与 paho

    我想对蚊子进行压力测试 所以我创建了一些代码 如下所示 for int i 0 i lt 800 i final int j i Thread t new Thread new Runnable Override public void r
  • 为什么 Sun Java 中的 HashSet 实现使用 HashMap 作为其支持?

    查看Java 6的源码 HashSet
  • 使用 SugarORM 和 GSON 解析字符串 id

    我在用着GSON创建一个SugarRecord来自 json 响应的对象 我使用的API返回一个名为 id 的字段 但 id 的类型是字符串 而不是long 后端使用mongo 下面是我正在使用的代码 Gson gson new Gson
  • 在 xaml 中创建字典?

    伪示例
  • 使用 JodaTime Instant 与 Hibernate 进行版本控制

    Using java time Instant与 Hibernate 一起工作 我正在使用hibernate java8 给出了更多的解决方案here https stackoverflow com a 26455446 581205 使用
  • 在 BLL 中处理异常并返回给客户端(winforms 或 webforms)?

    我正在寻找进行异常处理的最佳方法 例如 当业务逻辑层中发生错误时 使用 catch 停止方法并将事件返回到表示层的最佳方法是 这个活动应该包含什么内容 或者我应该总是冒泡异常并在表示层中处理它们 任何人都有一些很好的链接 并且需要阅读有关处
  • 在 SQLite 中转义表名?

    我在 SQLite 中有一个名为 References 的表 所以我似乎无法定位它 我用 SQLite studio 编辑数据库抛出错误 有没有办法转义数据库名称 查询是 UPDATE References SET DateTimeLast
  • 如何在 C# 中创建动态设置属性名称的 JSON 对象?

    我需要返回一个 JSON 对象数组 它是 SQL 查询的结果 SQL 查询可以是任何内容 因此我需要在代码中动态创建属性名称和值 例如 从员工中选择first name last name 我想返回 data first name dave
  • Angular 2 提交后如何清除表单?

    我有一些带有模板的简单 Angular 2 组件 提交后如何清除表单和所有字段 我无法重新加载页面 设置数据后date setValue 场依然touched import Component from angular2 core impo
  • WebLogic 12 SSLKeyException:重新启动后主机名验证失败

    我在 WebLogic 12 1 2 0 0 上部署了一个 WAR 文件 应用程序通过 HTTPS 调用 Web 服务 证书导入到 DemoTrust jks 中 所有 SSL 相关设置都应该正确 实际上它可以工作 但是在服务器重新启动后
  • 动态linq:有没有办法通过索引访问对象数据?

    我需要使用 Dynamic Linq 进行一些内存中过滤 我的对象只有一个索引器 public object this int index 对我的数据的访问如下 对象 0 对象 1 所以我的查询是这样的 get FilterText fro