什么是RequireQualifiedAccess属性?

时间:2017-06-09 16:05:00

标签: .net f#

来自docs

  

此属性用于指示对模块,记录或联合类型的元素的引用需要显式限定访问。

什么是明确的合格访问权限?什么是隐式访问?

3 个答案:

答案 0 :(得分:7)

也许一个具体的例子会有所帮助。

List模块具有此属性。这意味着您不能打开模块:

open List // compile error!

map id [1;2]

相反,你必须这样做:

List.map id [1;2]

答案 1 :(得分:5)

来自The About F# Page

  

[<RequireQualifiedAccess>]属性添加到模块表示可能未打开该模块,并且对模块元素的引用需要显式限定访问权限。例如,Microsoft.FSharp.Collections.List模块具有此属性。

     

当模块中的函数和值具有可能与其他模块中的名称冲突的名称并且要求合格访问可以极大地提高库的长期可维护性和可演化性时,这非常有用:可以将函数添加到模块中没有破坏源兼容性。

答案 2 :(得分:5)

F#列表,数组和序列的运算符行为在模块之间手动镜像,以便您可以以一致的方式使用这些结构。实现是不同的。

如果您更喜欢以隐式风格工作,那么设置起来很容易。就像你主要使用Lists一样,你可以这样做:

let inline map = List.map

etc.

也许将来,这种模块将从上下文中推断出来(即我们正在使用列表,所以显然 map 指的是 List.map < / em>的)。最终,这是一个语言设计问题。合理的违约应​​该是什么?默认值总是蔓延到更广泛的代码库中。平均而言,这个默认对程序员更有用吗?因此,RequireQualifiedAccess标志。有人认为这是明智的做法。什么是惯用的?这还有意义吗?

您引用的文档并非严格属实。以下是隐式(例如,我不需要使用完全限定的显式DicriminatedUnion.Case1):

type DiscinatedUnion = 
  | Case1
  | Case2
  | Case3

let f x =
  match x with
  | Case1 -> "case1"
  | Case2 -> "case2"
  | Case3 -> "case3"

f Case1

摘自专家F#

某些函数语言(如Haskell)允许您隐式传递操作字典 通过类型推断的扩展称为类型类。在撰写本文时,不支持此操作 通过F#,但F#的设计者表示他们希望该语言的未来版本能够得到支持 这个。无论哪种方式,显式传递操作字典在所有函数式编程中都很常见 并且是掌握的重要技术。