为什么xquery允许局部变量重新声明?

为什么xquery允许局部变量重新声明?,xquery,xquery-3.1,Xquery,Xquery 3.1,这甚至不会发出警告: xquery version "3.1"; let $a := 1 let $a := 2 return $a (: yields 2 in all runtimes I tested :) 为什么(函数式)编程语言允许重新声明变量? 我真的只是想弄清楚背后的理由。 我相信,通过在编译步骤中拒绝这一点,可以实现一些更积极的优化。 由于子作用域也知道局部变量,这就为难以捕获的错误留下了更多的空间。 JavaScript在var中使用了多年,最后通过引入let和const摆脱

这甚至不会发出警告:

xquery version "3.1";
let $a := 1
let $a := 2
return $a
(: yields 2 in all runtimes I tested :)
为什么(函数式)编程语言允许重新声明变量? 我真的只是想弄清楚背后的理由。 我相信,通过在编译步骤中拒绝这一点,可以实现一些更积极的优化。 由于子作用域也知道局部变量,这就为难以捕获的错误留下了更多的空间。 JavaScript在
var
中使用了多年,最后通过引入
let
const
摆脱了它

下面是一个很难跟踪值的示例

xquery version "3.1";
let $f := function ($c) {
  (: some code ... :)
  let $b := $a
  let $a := 2
  let $c := $b
  (: some more code ... :)
  return ($a, $b, $c)
}
let $a := 1
return ($a, $f($a), $a)
在评估之前,你可能想先猜一猜。

为什么”问题总是很难回答,因为你可以猜出为什么设计师可能做出了他们所做的决定,但通常不可能获得他们推理的历史证据。如果你想研究历史,工作组的档案可以在上找到,但是搜索设备不是特别好,所以你的工作会被删掉。但是,即使你在会议记录中找到了相关的讨论,它可能只记录了决定,而不是详细的论点

XSLT1.0不允许重新声明局部变量,我似乎记得XSL人员通常反对这样做,而XQuery人员通常支持这样做。双方都有争论。允许它的主要论据可能是“没有不必要的限制”论据:如果某个东西具有定义良好的语义,则不允许它。反对它的理由是人们可能会误用和误解它;他们认为,如果这两个变量的名称相同,那么它们一定有某种关联

Javascript的类比不是特别好,因为过程语言中的变量与函数语言中的变量有很大的不同


许多其他语言允许两个局部变量具有相同的名称,前提是它们具有不同的作用域。

感谢您提供的详细答案。和往常一样,这确实有助于我理解某些决策背后的历史。我绝对不同意的是JavaScript“只是”过程性的(请参阅)。我的观点是,我学会了喜欢编译器告诉我要注意什么。我不是说这应该被禁止(默认)。