可变值和不可变值重定义有什么区别?

2024-03-08

我读到 F# 中的值是不可变的。然而,我也遇到了重新定义价值定义的概念,它掩盖了以前的定义。这与可变值有何不同?我问这不仅是一个理论构造,而且还询问是否有关于何时使用可变值以及何时重新定义表达式的建议;或者如果有人可以指出后者不是惯用的 f#。

重新定义的基本示例:

let a = 1;;
a;; //1
let a = 2;;
a;; //2

更新1:

添加到下面的答案中,顶层 Fsharp 交互中的重新定义仅允许在不同的终端中。以下内容也会在 fsi 中引发错误:

let a = 1
let a = 2;;

Error: Duplicate definition of value 'a'

另一方面,let 绑定中允许重新定义。

更新2: 实际差异,闭包不能与可变变量一起使用:

let f =
   let mutable a = 1
   let g () = a //error
   0  
f;;

更新3:

虽然我可以使用参考来模拟副作用,例如:

let f =
   let  a = ref 1
   let g = a
   a:=2
   let x = !g  + !a
   printfn "x: %i" x //4

f;;

除了闭包使用上的差异之外,我不太明白重新定义和使用 mutable 关键字之间的实际差异,例如:

let f  =
   let a = 1
   let g  = a
   let a = 2
   let x = g + a
   printfn "x: %i" x //3

f;;

vs

let f =
   let mutable a = 1
   let g = a
   a <-2
   let x = g  + a
   printfn "x: %i" x //3
 f;;

另一种思路:我不确定如何使用线程,但是(a)另一个线程可以改变 let 绑定中的可变变量的值,(b)另一个线程可以重新绑定/重新定义 a 中的值名称吗?让绑定。我肯定在这里遗漏了一些东西。

更新4: 最后一种情况的区别在于,突变仍然会在嵌套作用域中发生,而嵌套作用域中的重新定义/重新绑定将“隐藏”外部作用域的定义。

let f =
   let mutable a = 1
   let g = a
   if true then
      a <-2   
   let x = g  + a
   printfn "x: %i" x //3

f;;

vs

let f =
   let a = 1
   let g = a
   if true then
      let a = 2  
      printfn "a: %i" a   
   let x = g  + a
   printfn "x: %i" x //2
f;;

我对F#不太熟悉,但我可以回答“理论”部分。

改变一个对象是(或者至少有可能是)全球可见副作用。引用同一对象的任何其他代码段都会观察到更改。现在可以更改程序中任何位置建立的依赖于对象值的任何属性。例如,如果您以影响其排序位置的方式改变列表中引用的对象,则列表已排序的事实可能会呈现为 false。这可能是一种极其不明显和非局部的效果 - 处理排序列表的代码和进行突变的代码可能位于完全独立的库中(两者都没有直接依赖于另一个库),仅通过长调用链连接(其中一些可能是其他代码设置的闭包)。如果您相当广泛地使用突变,那么两个位置之间甚至可能没有直接的调用链链接,事实上this可变对象最终被传递给that改变代码可能取决于程序迄今为止执行的特定操作顺序。

另一方面,将局部变量从一个不可变值重新绑定到另一个,从技术上讲可能仍然被视为“副作用”(取决于语言的确切语义),但它是一个相当本地化的变量。因为它只影响name,不在之前或之后value,对象来自哪里或者之后它们将去往哪里并不重要。它改变了意义only访问该名称的其他代码位;您必须仔细检查受此影响​​的代码的地方仅限于名称范围。这种副作用很容易保留在方法/函数/任何东西的内部,因此从外部角度来看,该函数仍然是无副作用的(纯粹的;引用透明的)——实际上没有捕获捕获的闭包名称而不是值 我相信这种本地重新绑定不可能成为外部可见的副作用。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

可变值和不可变值重定义有什么区别? 的相关文章

  • `ImmutableSortedSet` 和 fsharp `Set` 有什么区别?

    BCL引入了一组Immutable Collections http blogs msdn com b bclteam archive 2012 12 18 preview of immutable collections released
  • python函数返回函数[关闭]

    就目前情况而言 这个问题不太适合我们的问答形式 我们希望答案得到事实 参考资料或专业知识的支持 但这个问题可能会引发辩论 争论 民意调查或扩展讨论 如果您觉得这个问题可以改进并可能重新开放 访问帮助中心 help reopen questi
  • 在 C# 中实现记忆化 [关闭]

    Closed 这个问题需要多问focused help closed questions 目前不接受答案 我知道这个话题 记忆 已经被讨论了很多 比如here https stackoverflow com questions 285216
  • 当两个模式共享“when”子句时,模式匹配不完整

    A 共同的惊喜 https stackoverflow com q 18691622 2314532对于 F 初学者来说 以下事实是不完全匹配 let x y 5 10 match something with when x lt y gt
  • 什么样的函数被认为是“可组合的”?

    维基百科文章函数组合 计算机科学 https en wikipedia org wiki Function composition computer science says 就像数学中通常的函数组合一样 每个函数的结果作为下一个函数的参数
  • “函数是第一等值”这到底是什么意思?

    有人可以用一些很好的例子清楚地解释它吗 在解释函数式编程时 我在 Scala 中遇到了这句话 一流 并不是一个正式定义的概念 但它通常意味着一个实体具有三个属性 有可能used 不受限制 只要 普通 值可以 即从函数传递和返回 放入容器等
  • 纯函数怎么能做IO呢?

    我最近了解到莫纳德随机数 http hackage haskell org package MonadRandom 0 1 13 docs Control Monad Random Class html t 3aMonadRandom图书馆
  • 可选择将项目添加到 Scala 映射

    我正在寻找这个问题的惯用解决方案 我正在构建一个valScala 不可变 Map 并希望有选择地添加一项或多项 val aMap Map key1 gt value1 key2 gt value2 if condition key3 gt
  • 单位安全平方根

    我只是想知道如何以与 F 正确交互的方式编写用户定义的平方根函数 sqrt 单位制 http blogs msdn com andrewkennedy archive 2008 09 04 units of measure in f par
  • Haskell 入门

    这个问题的答案是社区努力 help privileges edit community wiki 编辑现有答案以改进这篇文章 目前不接受新的答案或互动 几天来 我一直试图理解 Haskell 中的函数式编程范例 我通过阅读教程和观看截屏视频
  • 如何判断何时创建新组件?

    我一直在寻找背后的逻辑当有人在 AngularJS Angular 上的 Web 应用程序中创建新组件时但我认为这更通用 可能适用于所有基于组件的前端框架 我知道有像这样的一些原则应该是抽象的和可重用的但例如我在角度文档中看到 每个单独的路
  • 在 Haskell 中合并两个列表

    无法弄清楚如何合并两个列表通过以下方式在哈斯克尔 INPUT 1 2 3 4 5 11 12 13 14 OUTPUT 1 11 2 12 3 13 4 14 5 我想提出一个更懒的合并版本 merge ys ys merge x xs y
  • 你能在 scala 中使用 varargs 柯里化一个函数吗?

    我正在考虑如何用可变参数柯里化一种方法 然后我意识到我什至不知道如何去做 理想情况下 它应该让您可以随时开始使用它 然后以可迭代结束 def concat strs String strs mkString val curriedConca
  • F# 尝试处理未处理的异常

    在下面的代码中 我想读取一个文件并返回所有行 如果存在 IO 错误 我希望程序退出并将错误消息打印到控制台 但程序仍然遇到未处理的异常 对此的最佳实践是什么 我想我不需要Some None因为无论如何我都希望程序在错误时退出 谢谢 let
  • 你为什么决定“反对”使用 Erlang?

    Locked 这个问题及其答案是locked help locked posts因为这个问题是题外话 但却具有历史意义 目前不接受新的答案或互动 你是否真的 尝试过 意味着在其中编程 而不仅仅是阅读有关它的文章 Erlang并决定在项目中不
  • 如何从引用的表达式匹配中获取模块、函数等的 F# 名称

    我继续开发 F 引用表达式的打印机 它不一定是完美的 但我想看看有什么可能 中的活跃模式Microsoft FSharp Quotations Patterns and Microsoft FSharp Quotations Derived
  • 卷积函数可以写成尾递归形式吗?

    我有一个函数 我想以尾递归形式编写 该函数计算求和的方法数k通过滚动s双面模具n次 我已经在上面看到了这个函数的数学解这个答案 https math stackexchange com questions 397689 why convol
  • 使用不区分大小写的比较从集合中减去记录

    我有一组记录 type Person Name string Age int let oldPeople set Name The Doctor Age 1500 Name Yoda Age 900 与上面的硬编码示例不同 这组数据实际上来
  • 使用 RxJava 限制吞吐量

    我现在遇到的情况很难解释 所以我会写一个更简单的版本来解释这个问题 我有一个Observable from 它发出一系列由ArrayList文件数量 所有这些文件都应上传到服务器 为此 我有一个函数可以完成这项工作并返回一个Observab
  • 带有“final”修饰符的“val”属性的用途是什么?

    最近IntelliJ建议添加final到一个val特性 这个特殊的属性是在init 堵塞 我试图找出什么是语义final val构造以及何时应该使用它 但 Kotlin 的核心在于不变性以及如何使用它val相当于final在 Java 中

随机推荐

  • Java生成带占位符的字符串

    我正在寻找一些东西来实现以下目标 String s hello s generate s new Object world assertEquals s hello world should be true 我可以自己写 但在我看来 我曾经
  • 防止 javascript setInterval 函数堆积

    我有一个在单击事件上运行的函数 该函数对我的一些动画 我正在做一个游戏 使用javascript的setIterval 所以问题是 如果用户在动画仍在显示时单击 setInterval仍在执行 则setInterval在事件堆栈中堆积 或者
  • 如何在 500,000 个点的 100 维空间中找到最近的 2 个点?

    我有一个 100 维空间中有 500 000 个点的数据库 我想找到最接近的 2 个点 我该怎么做 更新 空间是欧几里得的 抱歉 并感谢所有的答案 顺便说一句 这不是家庭作业 里面有一章算法简介 http en wikipedia org
  • .forEach 完成后执行回调函数

    我试图在 forEach 循环完成所有迭代后执行一个函数 This answer https stackoverflow com a 18983245 3976696提供了一个有趣的解决方案 但我无法让它发挥作用 这是我改编的代码 创建了一
  • 将 Android 库导出为 AAR 文件

    我在我的项目中创建了一个库模块 现在 我想与其他人分享 发布这个库 目前共享 aar 文件就可以了 我浏览了这篇文章 https developer android com studio projects android library h
  • Maven:生命周期阶段与目标之间的关系

    我很难在某些 Maven 概念中看到 树木中的森林 我知道 Maven 预先配置了一系列所谓的 构建生命周期阶段 开头为validate and test并结束于deploy 我从 Ant 转向 Maven 在 Ant 中 您将主要构建阶段
  • mysql_insert_id 或类似的东西返回最后一个 mysql UUID()

    如何返回最后生成的 UUID 主键 有类似 mysql insert id 的东西吗 Table uuidtable primary key uuid uuid id u index integer 多个 id u 与主键 uuid 匹配
  • 如何使 rake 测试不使用默认的 minitest?

    我正在跟随制作你自己的宝石 http guides rubygems org make your own gem来自 RubyGems 的指南 执行rake test指令失败如下 gt rake test rbenv versions 2
  • 使用 Backbone 将文件上传到 tastypie?

    检查了一些其他问题 我认为我的 tastypie 资源应该如下所示 class MultipartResource object def deserialize self request data format None if not fo
  • 聚类——稀疏向量和稠密向量

    对于聚类 Mahout 输入需要采用向量形式 有两种类型的向量实现 一种是稀疏向量 另一种是密集向量 两者有什么区别 稀疏和密集的使用场景 从概念上讲 稀疏向量中的大多数值都为零 而在稠密向量中则不是 对于稠密矩阵和稀疏矩阵也是如此 条款s
  • emacs 窗口中的文本居中

    在一个孤独的 emacs 框架内 我频繁地在编辑 70 列文本文件 LaTeX 和 120 列程序 h cpp 文件 之间切换 我想继续仅使用一个 emacs 框架 而不调整其大小或创建其他框架 问题就在这里 我的窗口宽度大约适合编辑 12
  • 使用未选中的复选框,如何过滤掉始终隐藏的 NSFW 标记的 div,但选中打开时,以遵循可见性规则?

    这个问题基于这个问题 答案 同时使用复选框和下拉菜单进行准确过滤 https stackoverflow com q 68317206 4383420 Hi 注意 简化的问题和代码位于代码笔或下面的代码片段中 这里我只是解释上下文 Imag
  • 将 FutureBuilder 与 setState 一起使用

    如何使用FutureBuilder with setState适当地 例如 当我创建一个有状态小部件时 它开始加载数据 FutureBuilder 然后我应该用新数据更新列表 所以我使用 setState 但它开始无限循环 因为我再次重建小
  • 如何使用 bnd/maven-bundle-plugin 将资源文件从 jar 依赖项包含到 osgi 包中?

    我在用着maven bundle plugin bnd有效地 从源中包含资源文件很简单 例如 资源文件 src main resources some xml 移至下面target目录 target classes some xml 在构建
  • 在 Backbone.js 中实现 Backbone.Subset.js 以从父集合中过滤模型

    In 这个 stackoverflow 帖子 https stackoverflow com questions 6865174 backbone js correct way of filter collection data and d
  • 如何获取 ntile() 的间隔

    我试图弄清楚是否有一种方法可以获取用于何时的间隔ntile 用来 我有一个样本 我想将其用作获取较大样本的百分位值的基础 并且我希望找到一种方法来获取使用时的间隔值ntile 对此的任何启发将不胜感激 我真的很想把这个作为评论 但我仍然无法
  • 手动删除 anaconda python 中 pkgs 文件夹中的所有文件是否安全?

    我运行这个命令来释放 anaconda 上的磁盘空间 conda clean all 但是 仍然有一些大文件残留在pkgsanaconda python 中的文件夹 手动删除其中的所有文件是否安全pkgs文件夹 有破坏我的 anaconda
  • Invoke-Restmethod:如何获取返回码?

    有没有办法在调用时将返回码存储在某处Invoke RestMethod在 PowerShell 中 我的代码如下所示 url http www dictionaryapi com api v1 references collegiate x
  • 如何从字符串中获取size_t?

    我需要从用户输入中获取数组大小 对我来说 将输入存储为很自然size t 但是正在寻找合适的strto 功能我找不到 我刚用过strtoull since unsigned long long保证至少是 64 位 而且我无论如何都使用 C9
  • 可变值和不可变值重定义有什么区别?

    我读到 F 中的值是不可变的 然而 我也遇到了重新定义价值定义的概念 它掩盖了以前的定义 这与可变值有何不同 我问这不仅是一个理论构造 而且还询问是否有关于何时使用可变值以及何时重新定义表达式的建议 或者如果有人可以指出后者不是惯用的 f