- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我正在研究具有深/浅绑定(bind)的动态/静态作用域,并手动运行代码以了解这些不同的作用域/绑定(bind)实际上是如何工作的。我阅读了理论并在谷歌上搜索了一些示例练习,我发现这些练习非常简单(例如 this one 这对动态作用域非常有帮助)但是我无法理解静态作用域的工作原理。
在这里,我发布了一个练习,以检查我是否获得了正确的解决方案:
考虑以下用伪代码编写的程序:
int u = 42;
int v = 69;
int w = 17;
proc add( z:int )
u := v + u + z
proc bar( fun:proc )
int u := w;
fun(v)
proc foo( x:int, w:int )
int v := x;
bar(add)
main
foo(u,13)
print(u)
end;
屏幕上打印的内容
a) 使用静态作用域?答案=180
b) 使用动态作用域和深度绑定(bind)?答案=69(u的总和=126,但它是foo的本地v,对吧?)
c) 使用动态作用域和浅绑定(bind)? answer=69(u 的总和 = 101,但它是 foo 的本地 v,对吧?)
PS:我正在尝试做一些这样的练习,如果你知道我在哪里可以找到这些类型的问题(最好有解决方案),请提供链接,谢谢!
最佳答案
您对词法(静态)范围的回答是正确的。您对动态范围的回答是错误的,但如果我正确地阅读了您的解释,那是因为您在 u
和 v
之间感到困惑,而不是因为对深度和浅层绑定(bind)的工作原理。 (我假设您的 u
/v
混淆只是偶然的,而不是由于对 foo< 的调用中的值与引用的奇怪混淆
。)
a) using static scope? answer=180
正确。
b) using dynamic scope and deep binding? answer=69 (sum for u = 126 but it's foo's local v, right?)
您的括号解释是正确的,但您的答案是错误的:u
确实设置为126
,并且foo
确实本地化了 v
,但由于 main
打印 u
,而不是 v
,所以答案是 126
。
c) using dynamic scope and shallow binding? answer=69 (sum for u = 101 but it's foo's local v, right?)
u
的总和实际上是 97
(42+13+42
),但由于 bar
本地化u
,答案是42
。 (您的括号解释对此是错误的 - 您似乎在解释语句 int u := w 时使用了全局变量
在 w
,即 17
bar
的定义中;但该语句实际上引用了 foo
的局部变量 w
,它的第二个参数,即13
。但这实际上并不影响答案。您的答案对于这个答案是错误的,只是因为 main
打印 u
,而不是 v
。)
对于词法范围,通过将伪代码翻译成具有词法范围的语言来检查您的答案非常容易。同样具有浅绑定(bind)的动态作用域。 (事实上,如果您使用 Perl,您几乎可以同时测试这两种方式,因为它支持这两种方式;只需使用 my
作为词法范围,然后执行查找和替换将其更改为 local
表示动态作用域。但是,即使您使用 JavaScript 表示词法作用域,使用 Bash 表示动态作用域,也应该可以快速测试两者。)
具有深度绑定(bind)的动态作用域要棘手得多,因为很少有广泛部署的语言支持它。如果您使用 Perl,则可以通过使用从变量名映射到标量引用的哈希(关联数组)并将此哈希从一个函数传递到另一个函数来手动实现它。在伪代码声明局部变量的任何地方,您都将现有的标量引用保存在 Perl 词法变量中,然后将新的映射放入哈希中;在函数结束时,恢复原始标量引用。为了支持绑定(bind),您可以创建一个包装函数,该函数创建哈希的副本,并将该传递给其包装函数。下面是使用该方法在 Perl 中动态范围、深度绑定(bind)的程序实现:
#!/usr/bin/perl -w
use warnings;
use strict;
# Create a new scalar, initialize it to the specified value,
# and return a reference to it:
sub new_scalar($)
{ return \(shift); }
# Bind the specified procedure to the specified environment:
sub bind_proc(\%$)
{
my $V = { %{+shift} };
my $f = shift;
return sub { $f->($V, @_); };
}
my $V = {};
$V->{u} = new_scalar 42; # int u := 42
$V->{v} = new_scalar 69; # int v := 69
$V->{w} = new_scalar 17; # int w := 17
sub add(\%$)
{
my $V = shift;
my $z = $V->{z}; # save existing z
$V->{z} = new_scalar shift; # create & initialize new z
${$V->{u}} = ${$V->{v}} + ${$V->{u}} + ${$V->{z}};
$V->{z} = $z; # restore old z
}
sub bar(\%$)
{
my $V = shift;
my $fun = shift;
my $u = $V->{u}; # save existing u
$V->{u} = new_scalar ${$V->{w}}; # create & initialize new u
$fun->(${$V->{v}});
$V->{u} = $u; # restore old u
}
sub foo(\%$$)
{
my $V = shift;
my $x = $V->{x}; # save existing x
$V->{x} = new_scalar shift; # create & initialize new x
my $w = $V->{w}; # save existing w
$V->{w} = new_scalar shift; # create & initialize new w
my $v = $V->{v}; # save existing v
$V->{v} = new_scalar ${$V->{x}}; # create & initialize new v
bar %$V, bind_proc %$V, \&add;
$V->{v} = $v; # restore old v
$V->{w} = $w; # restore old w
$V->{x} = $x; # restore old x
}
foo %$V, ${$V->{u}}, 13;
print "${$V->{u}}\n";
__END__
实际上它打印了126
。这显然很困惑且容易出错,但它也确实可以帮助您了解正在发生的事情,因此出于教育目的,我认为这是值得的!
关于具有深/浅绑定(bind)的动态/静态范围(练习),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3869040/
我不能解决这个问题。和标题说的差不多…… 如果其他两个范围/列中有“否”,我如何获得范围或列的平均值? 换句话说,我想计算 A 列的平均值,并且我有两列询问是/否问题(B 列和 C 列)。我只希望 B
我知道 python 2to3 将所有 xrange 更改为 range 我没有发现任何问题。我的问题是关于它如何将 range(...) 更改为 list(range(...)) :它是愚蠢的,只是
我有一个 Primefaces JSF 项目,并且我的 Bean 注释有以下内容: @Named("reportTabBean") @SessionScoped public class Report
在 rails3 中,我在模型中制作了相同的范围。例如 class Common ?" , at) } end 我想将公共(public)范围拆分为 lib 中的模块。所以我试试这个。 module
我需要在另一个 View 范围 bean 中使用保存在 View 范围 bean 中的一些数据。 @ManagedBean @ViewScoped public class Attivita impl
为什么下面的代码输出4?谁能给我推荐一篇好文章来深入学习 javascript 范围。 这段代码返回4,但我不明白为什么? (function f(){ return f(); functio
我有一个与此结构类似的脚本 $(function(){ var someVariable; function doSomething(){ //here } $('#som
我刚刚开始学习 Jquery,但这些示例对我帮助不大...... 现在,以下代码发生的情况是,我有 4 个表单,我使用每个表单的链接在它们之间进行切换。但我不知道如何在第一个函数中获取变量“postO
为什么当我这样做时: function Dog(){ this.firstName = 'scrappy'; } Dog.firstName 未定义? 但是我可以这样做: Dog.firstNa
我想打印文本文件 text.txt 的选定部分,其中包含: tickme 1.1(no.3) lesson1-bases lesson2-advancedfurther para:using the
我正在编写一些 JavaScript 代码。我对这个关键字有点困惑。如何在 dataReceivedHandler 函数中访问 logger 变量? MyClass: { logger: nu
我有这个代码: Public Sub test() Dim Tgt As Range Set Tgt = Range("A1") End Sub 我想更改当前为“A1”的 Tgt 的引
我正忙于此工作,以为我会把它放在我们那里。 该数字必须是最多3个单位和最多5个小数位的数字,等等。 有效的 999.99999 99.9 9 0.99999 0 无效的 -0.1 999.123456
覆盖代码时: @Override public void open(ExecutionContext executionContext) { super.open(executio
我想使用 preg_match 来匹配数字 1 - 21。我如何使用 preg_match 来做到这一点?如果数字大于 21,我不想匹配任何东西。 example preg_match('([0-9]
根据docs range函数有四种形式: (range) 0 - 无穷大 (range end) 0 - 结束 (range start end)开始 - 结束 (range start end st
我知道有一个UISlider,但是有人已经制作了RangeSlider(用两个拇指吗?)或者知道如何扩展 uislider? 最佳答案 我认为你不能直接扩展 UISlider,你可能需要扩展 UICo
我正在尝试将范围转换为列表。 nums = [] for x in range (9000, 9004): nums.append(x) print nums 输出 [9000] [9
请注意:此问题是由于在运行我的修饰方法时使用了GraphQL解析器。这意味着this的范围为undefined。但是,该问题的基础知识对于装饰者遇到问题的任何人都是有用的。 这是我想使用的基本装饰器(
我正在尝试创建一个工具来从网页上抓取信息(是的,我有权限)。 到目前为止,我一直在使用 Node.js 结合 requests 和 Cheerio 来拉取页面,然后根据 CSS 选择器查找信息。我已经
我是一名优秀的程序员,十分优秀!