为什么我不能把这个字符串变成文字?

时间:2017-03-02 19:56:20

标签: f# constant-expression

我需要将字符串转换为Literal,以便将其作为参数传递给CsvProvider。但我无法做到。下面的代码运行没有问题:

open System.IO
open FSharp.Data
open FSharp.Data.JsonExtensions

let charSwitch (a: char) b x =
    if x = a then
        b
    else
        x

let jsonDataPath = Path.Combine(__SOURCE_DIRECTORY__, @"data\fractal.json")
let jsonData = JsonValue.Load(jsonDataPath)

/// Path with traded assets
let trp = ((jsonData?paths?tradedAssets).AsString() |> Core.String.map (charSwitch '\\' '/')).ToString()
printfn "trp is a standard string: %s" trp
// trp is a standard string: H:/Dropbox/Excel/Data/Fractal/Traded.csv

但是,添加以下两行时

[<Literal>]
let tradedPath = trp

最后我收到了消息This is not a valid constant expression or custom attribute value

我甚至试图制作一份trp副本,但这没有帮助。

有什么方法可以解决这个问题?

2 个答案:

答案 0 :(得分:5)

可悲的是,通过对其应用[<Literal>]属性,您无法将普通值神奇地转换为文字值。

关于文字值的特殊之处在于它被编译为常量,这意味着它们必须在编译时可以确定。

例如,这是一个文字字符串:

[<Literal>]
let testLiteral = "This is a literal string"

您可以将多个文字字符串组合成一个新的文字字符串:

[<Literal>]
let a = "a"
[<Literal>]
let b = "b"
[<Literal>]
let ab = a + b

您不能将任意函数应用于文字,因为它们在编译时无法确定。

More about literals.

答案 1 :(得分:3)

查看您最后的评论,您尝试使用CsvProvider,当然可以使用其他内容来解析csv文件,但也可以使用{{1}在[<Litera>]上,并向提供者提供一个ResolutionFolder参数(这必须是Literal)。下面是两个示例,一个使用Project根目录中的示例来创建类型,然后使用命令行参数作为实际文件。另一个使用相对路径来解析文件。

__SOURCE_DIRECTORY__

输出:

enter image description here