将一个非常Python式的库移植到.NET

本文关键字:NET Python 非常 一个 | 更新日期: 2023-09-27 18:33:09

我正在研究将Python库Beautiful Soup移植到.NET的可能性。 主要是因为我真的很喜欢解析器,而且在.NET框架上根本没有好的HTML解析器(Html Agility Pack已经过时,有缺陷,没有文档记录,除非知道确切的模式,否则无法正常工作。

我的主要目标之一是让基本的 DOM 选择功能真正与 BeautifulSoup 的美丽和简单性并行,允许开发人员轻松制作表达式以找到他们正在寻找的元素。

BeautifulSoup利用松散绑定和命名参数来实现这一点。 例如,要查找idtest 的所有 a 标签和包含单词 footitle,我可以执行以下操作:

soup.find_all('a', id='test', title=re.compile('foo'))

但是,C# 没有任意数量的命名元素的概念。 这。NET4 运行时已命名参数,但它们必须与现有方法原型匹配。

我的问题:与这个 Pythonic 结构最相似的 C# 设计模式是什么?

一些想法:

我想根据我作为开发人员想要如何编码来追求这一点。 实现这一点超出了本文的范围。 我的一个想法是使用匿名类型。 像这样:

soup.FindAll("a", new { Id = "Test", Title = new Regex("foo") });

虽然这种语法松散地匹配 Python 实现,但它仍然有一些缺点。

  1. FindAll实现必须使用反射来分析匿名类型,并以合理的方式处理任何任意元数据。
  2. FindAll原型需要Object,这使得除非你非常熟悉记录的行为,否则相当不清楚如何使用该方法。 我不相信有办法声明必须采用匿名类型的方法。

我的另一个想法也许是一种更 .NET 的方式来解决这个问题,但偏离了库的 Python 根。 那就是使用流畅的模式。 像这样:

soup.FindAll("a")
    .Attr("id", "Test")
    .Attr("title", new Regex("foo"));

这需要构建表达式树并在 DOM 中查找相应的节点。

我的第三个也是最后一个想法是使用 LINQ。 像这样:

var nodes = (from n in soup
             where n.Tag == "a" &&
             n["id"] == "Test" &&
             Regex.Match(n["title"], "foo").Success
             select n);

我希望任何有将 Python 代码移植到 C# 经验的人提供任何见解,或者只是关于处理这种情况的最佳方法的总体建议。

将一个非常Python式的库移植到.NET

你是否尝试在IronPython引擎中运行你的代码。据我所知,它的性能非常好,你不必接触你的python代码。