【问题标题】:What types of languages allow programmatic creation of variable names?哪些类型的语言允许以编程方式创建变量名?
【发布时间】:2011-03-04 04:45:10
【问题描述】:

这个问题纯粹出于求知欲。

相对经常地浏览 Python 部分,我看到了许多类似于 this 的问题,其中有人要求以编程方式定义全局变量。他们中的一些人知道exec 的陷阱,而其他人则没有。

但是,我最近一直在 Stata 中进行编程,以下是常见的:

local N = 100
local i = 1

foreach x of varlist x1 - x`N' {
    local `x' = `i' * `i'
    ++i 
}

用 Stata 的说法,创建一个名为 N 的本地宏,N 的计算结果为 100。在 foreach 循环的每次迭代中,从 x1x100 的值被分配给本地宏x。然后,循环内的行将i 的平方分配给x 的扩展,这是一个与i 结尾相同的局部宏。也就是说,在这个循环之后,x4 扩展为 4^2,x88 扩展为 88^2。

在 Python 中,执行类似操作的方法是:

squares = {}

for x in range(1,101):
    squares[x] = x**2

那么squares[7] 等于 7^2。

这是一个非常简单的例子。 stata 宏还有很多其他用途。您可以将它们用作传递要评估的函数的一种方式,例如:

local r1 "regress"
local r2 "corr"

foreach r of varlist r1-r2 {
     ``r'' y x
}

r 周围的双刻度线将该宏扩展了两次,首先是 r1/r2,然后是 regress/corr,运行线性回归的结果是 y 作为依赖项和x作为自变量,然后显示yx之间的相关性。更复杂的东西是可能的。

我的问题基本上是,stata 是否属于某种更大的语言类别,其中变量赋值/评估采用这种“宏赋值/扩展”形式?任何解释为什么会这样设计一种语言,和/或其他语言中类似结构的示例的任何解释都会加分。

【问题讨论】:

    标签: python variable-assignment stata stata-macros


    【解决方案1】:

    这实际上只是存在多少语法糖的问题。在任何有价值的语言中,您都可以使用映射或字典数据结构在运行时创建具有某些值的变量名(键)。有些语言可能比其他语言更透明地将其与普通变量标识符集成。

    【讨论】:

      【解决方案2】:

      (对不起,这是一个“答案”,而不是评论……人们不评价我的答案,所以我没有足够的分数来评论这个问题。)

      首先,让我指出 Stata 的奇怪之处在于它会在执行那行代码之前翻译宏。例如:

      假设你打字。

      local x3 = 20 
      local y = 3 
      display "I am `x`y'' years old"
      

      在内部,Stata 将翻译本地变量(从内到外),然后执行display 命令。 也就是Stata会翻译命令

      display "I am `x3' years old"
      

      然后

      display "I am 20 years old"
      

      那么,Stata 将实际执行最后一行代码。您可以通过首先执行以下命令来观看所有这些:set trace on

      有细微的差别。 ` ' 括号更改命令。我认为这实际上与其他编程语言不同。您通常可以在 Stata 中用一行代码来做某事,而其他语言需要两行代码(一行用于“扩展”宏;另一行用于执行代码行)。

      这方面的有用之处在于,Stata 还可以计算 ` ' 括号内的各种表达式(只要它们返回一个数字或字符串......例如,没有返回矩阵)

      display "I am `= 2011 - 1991' years old"
      display "I am `= floor(uniform()*`x`y'')' years old"
      

      一旦你习惯了,这将非常有用。宏使 Stata 中的东西方式 比您在 SAS 中所做的更干净。 SAS 的 %let 语句没有那么灵活。

      我还要指出一些错误。

      (1) 在这些示例中,循环设置错误。 x1, x2, ... , x100 是宏(本地),而不是变量。你不能说foreach x of varlist x1 - x100 因为x1-x100 不是一个变量列表。如果我想这样做,我可能会使用:

      local N = 100
      forvalues i = 1/`N' {
          local x`i' = `i' * `i'
      }
      

      第二个例子也犯了同样的错误。 r1r2 不是变量。 你可以这样做:

      local mycommands regress corr 
      foreach r in `mycommands' {
           `r' y x
      }
      

      (虽然我实际上会输入等价的 foreach r of local mycommands { ... },据说执行起来要快一点)。

      (2) 其次,++i 无效。你可能是想说local ++i

      【讨论】:

        【解决方案3】:

        我不知道这是否是你要找的,但在 PHP 中你可以做到:

        for ($i=0; $i<10; $i++) {
            ${x.$i} = $i*$i;
        }
        
        print $x3; // prints 9
        print $x4; // prints 16
        

        我个人觉得这很不愉快。

        【讨论】:

          【解决方案4】:

          Javascript 是一个明显的例子,虽然机制类似于 Python,而不是 Stata。

          for(var i = 0; i < 100; i++)
              this["var" + i] = i * i;
          
          alert(var8); // 64
          

          【讨论】:

            猜你喜欢
            • 2017-12-26
            • 2011-02-21
            • 1970-01-01
            • 2011-07-14
            • 2011-05-04
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2011-02-28
            相关资源
            最近更新 更多