Sol*_*lma 4 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
Run Code Online (Sandbox Code Playgroud)
但是,添加以下两行时
[<Literal>]
let tradedPath = trp
Run Code Online (Sandbox Code Playgroud)
最后我得到了消息This is not a valid constant expression or custom attribute value.
我甚至试图复制trp,但这没有帮助.
有什么办法可以绕过这个问题吗?
遗憾的是,通过将[<Literal>]属性应用于它,您无法将普通值神奇地转换为文字值.
关于文字值的特殊之处在于它被编译为常量,这意味着它们必须在编译时可以确定.
例如,这是一个文字字符串:
[<Literal>]
let testLiteral = "This is a literal string"
Run Code Online (Sandbox Code Playgroud)
您可以将多个文字字符串组合成一个新的文字字符串:
[<Literal>]
let a = "a"
[<Literal>]
let b = "b"
[<Literal>]
let ab = a + b
Run Code Online (Sandbox Code Playgroud)
您不能将任意函数应用于文字,因为它们在编译时无法确定.
看看你尝试使用的最后一条评论CsvProvider,你当然可以使用其他东西来解析csv文件,但也可以使用[<Litera>]以及__SOURCE_DIRECTORY__给出一个ResolutionFolder参数(虽然这必须是一个文字)给提供商。以下是两个示例,其中一个使用项目根目录中的示例来创建类型,但随后使用实际文件的命令行参数。另一种使用相对路径来解析文件。
open System
open FSharp.Data
open FSharp.Data.JsonExtensions
#if INTERACTIVE
#r @"..\packages\FSharp.Data.2.3.2\lib\net40\FSharp.Data.dll"
#endif
[<Literal>]
let file = __SOURCE_DIRECTORY__ + @"\file1.csv"
[<Literal>]
let path3 = __SOURCE_DIRECTORY__
[<Literal>]
let path4 = "."
type SampleFile = CsvProvider<file,HasHeaders=true>
type SampleFile3 = CsvProvider<"file1.csv",HasHeaders=true,ResolutionFolder=path3>
[<EntryPoint>]
let main argv =
//let nonLiteralPath = @".\file1.csv" // you could hardcode this in the file but:
let nonLiteralPath = argv.[0] // you can also use a path specified on the command line
let DataFile = SampleFile.Load(nonLiteralPath)
[for row in DataFile.Rows -> row.``Key #1``] |> printfn "%A"
let x= SampleFile3.GetSample() // use a relative path, this will be the root of the project at design time
// or the root of the exe at the execution time
[for row in x.Rows -> row.``Key #2``] |> printfn "%A"
printfn "%A" argv
Run Code Online (Sandbox Code Playgroud)
对于输出: