4

我不认为它可能,但你能做类似的事情来允许通过类型扩展进行自定义格式化吗?

[<StructuredFormatDisplayAttribute("Rate: {PrettyPrinter}")>]
type Rate with 
    member x.PrettyPrinter = x.Title + string x.Value

注意:它看起来可以作为内部扩展(相同的程序集),但不能作为可选扩展

如果不是,我猜这可能是一个功能请求,除非有人有一个不错的选择?

4

2 回答 2

2

正如您所说,StructuredFormatDisplayAttribute仅适用于编译为属性的成员(包括标准属性、相同的程序集扩展,但不包括扩展成员)。在封面下,它是使用反射访问的(如您所见,它也可以是私有的):

let getProperty (obj: obj) name =
    let ty = obj.GetType()
    ty.InvokeMember(name, (BindingFlags.GetProperty ||| BindingFlags.Instance ||| 
        BindingFlags.Public ||| BindingFlags.NonPublic), 
        null, obj, [| |],CultureInfo.InvariantCulture)

如果您出于调试目的需要此属性,则该DebuggerTypeProxy属性可能是一种替代方法(请参阅MSDN 文档)。这允许您将原始类型替换为用于在调试器中显示类型的代理类型。(但我认为属性仍然必须放在实际的类型定义上,而不是放在扩展上。)

于 2012-10-02T14:44:16.377 回答
2

不,这是不可能的。在 FSI 中,您可以使用fsi.AddPrinter自定义输出。

fsi.AddPrinter (fun (x: Rate) -> x.Title + string x.Value)

编辑

对于一般字符串格式,您可以使用Printf格式%a说明符。一些额外的功能可以使这更方便。

[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
module Rate =
  let stringify (x: Rate) = x.Title + string x.Value
  let print rate = printf "%s" (stringify rate)

printf "Rate: %a" (fun _ -> Rate.print) rate
let formattedString = sprintf "Rate: %a" (fun _ -> Rate.stringify) rate
于 2012-10-02T14:07:35.523 回答