【问题标题】:F# Xml TypeProvider for C#C# 的 F# Xml TypeProvider
【发布时间】:2013-08-14 22:49:13
【问题描述】:

在 C# 中是否有与 F# TypeProvider 等效的内容?我正在寻找使用 C# 读取 Xml 文件的最简单方法。在这一点上,我打算使用 XDocument,但我想知道是否有更好的东西。

F# 使读取 Xml 文件变得如此容易,以至于我想知道我是否不应该为 Xml 处理切换语言!

【问题讨论】:

    标签: c# .net f# type-providers f#-data


    【解决方案1】:

    如前所述,C# 不支持类型提供程序,并且没有简单的方法来模拟它们(正如 Gustavo 提到的,您可以通过小型 F# 库使用生成的类型提供程序,但 XML、JSON , CSV 等不是这种。)

    我认为使用 F# 库进行处理是最好的方法。

    更复杂的替代方法是编写代码,让您定义类型以在 C# 中对 XML 文件进行建模,然后自动将文件读入这些类。我认为不存在这样的东西,但我在 F# 中写了一个类似的东西(在类型提供程序之前),所以你可以看到the snippet for inspiration。用法如下:

    // Modelling RSS feeds - the following types define the structure of the
    // expected XML file. The StructuralXml parser can automatically read
    // XML file into a structure formed by these types.
    type Title = Title of string
    type Link = Link of string
    type Description = Description of string
    
    type Item = Item of Title * Link * Description
    type Channel = Channel of Title * Link * Description * list<Item>
    type Rss = Rss of Channel
    
    // Load data and specify that names in XML are all lowercase
    let url = "http://feeds.guardian.co.uk/theguardian/world/rss"
    let doc : StructuralXml<Rss> = 
      StructuralXml.Load(url, LowerCase = true)
    
    // Match the data against a type modeling the RSS feed structure
    let (Rss(channel)) = doc.Root
    let (Channel(_, _, _, items)) = channel
    for (Item(Title t, _, _)) in items do
      printfn "%s" t
    

    【讨论】:

      【解决方案2】:

      您是否有任何理由无法将 F# 库添加到您的解决方案中?该项目可以在您想要的 XML 上创建抽象,并且您可以从您的 C# 项目中使用它。

      【讨论】:

        【解决方案3】:

        不,不能直接在 C# 中使用类型提供程序。

        对于生成的类型提供程序,您可以在 F# 项目中“实例化”类型提供程序,然后在 C# 中使用它,但这不适用于已擦除的类型提供程序,例如 CsvProviderJsonProviderXmlProviderFreebaseWorldbank。 (它适用于内置的 SqlProvider 和 WsdlProvider,不过)。

        已经讨论过将 CsvProviderJsonProviderXmlProvider 切换到生成的模型,以便它们可用于 C# (https://github.com/fsharp/FSharp.Data/issues/134#issuecomment-20104995) 中的数据绑定,但这可能需要一段时间发生。

        我的建议是要么完全切换到 F#,要么创建反映类型提供程序创建的类型的记录类型。示例:

        type T = {
            A : int
            B : string
            (...)
        }
        
        type XmlT = XmlProvider<"xml file">
        
        let getXml() =
            let xml = XmlT.GetSample()
            { A = xml.A
              B = xml.B
              (...) }
        

        【讨论】:

          【解决方案4】:

          我查看了您在 F# 中指向 XmlProvider 的链接,但在 C# 中没有看到类似的内容。我经常使用带有 Xml 的 C#,并且经常使用 XDocument 和 XElement 来加载和解析 Xml。一旦我将 Xml 加载到 XDocument 中,我就会使用 Linq to Xml 来执行类似的事情。我经常使用 Linq Pad 对 Xml 进行一般查询,这与 C# 很好用,但不确定 F#。

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多