'var a = 2' 之间的区别和“this.a = 2”
我刚刚在一些处理 RegExp.test
的 javascript 代码中发现了最奇怪的错误。我在函数内声明了一个正则表达式 regexp ,并且有一个引用 regexp 的闭包,并且我使用该闭包迭代要测试的字符串数组借助来自prototype.js的collect
,即
function some_func() {
var regexp = /regular_expression/;
an_array_of_strings.collect(
function(str) {
if (regexp.test(str)) {
do_something();
}
}
);
}
真正奇怪的是,在闭包内调用regexp.test(str)
会在true<之间交替/code> 和
false
在同一输入上。我查看了 RegExp.test
的源代码,没有发现任何可疑之处,但确实发生了一些事情,因为同一个字符串如何能够通过和失败相同的正则表达式。在仔细研究了 RegExp.test
后,我基本上得出结论,在 RegExp.test
中声明的变量在调用之间继续存在,并且扰乱了后续调用。 什么区别
this.a = 2;
有
var a = 2;
所以问题是:上述语句出现在对持有该对象引用的闭包内的对象调用的方法中, ?我这么问是因为当我将 regexp.test
移到闭包之外时,错误就会消失。当在闭包外部调用 regexp.test 时,它不会在每次调用时在 true 和 false 之间翻转。我不知道为什么会发生这种情况。
编辑:当我将regexp
移到闭包之外时,我忘记添加全局选项,这就是错误消失的原因。谢谢伊沃。
I just discovered the weirdest bug in some javascript code dealing with RegExp.test
. I had a regular expression regexp
declared inside a function and I had a closure that had a reference to regexp
and I was using the closure to iterate over an array of strings to test them with the help of collect
from prototype.js, i.e.
function some_func() {
var regexp = /regular_expression/;
an_array_of_strings.collect(
function(str) {
if (regexp.test(str)) {
do_something();
}
}
);
}
The really weird thing was that calling regexp.test(str)
inside the closure would alternate between true
and false
on the same input. I looked at the source for RegExp.test
and I didn't see anything fishy but there was something going on because how can the same string pass and fail the same regular expression. After staring some more at RegExp.test
I basically concluded that variables declared in RegExp.test
were continuing to exist between invocations and were messing up subsequent invocations. So here's the question: What is the difference between
this.a = 2;
and
var a = 2;
when the above statements appear inside a method being called on an object inside a closure that holds a reference to that object? I'm asking because the bug disappears when I move regexp.test
outside the closure. When regexp.test
is called outside the closure then it doesn't flip-flop between true
and false
on each call. I have no idea why this is happening.
Edit: When I was moving the regexp
outside the closure I was forgetting to add the global option so that's why the bug was disappearing. Thanks Ivo.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
由于您没有显示您的正则表达式,但我只是回答了与此类似的问题,我想您在正则表达式中使用了
global
选项,这有一些有趣的副作用。来源:https://developer.mozilla.org/en/JavaScript/ Reference/Global_Objects/RegExp/test
所以这里到底发生的是,由于您使用正则表达式的全局选项,它将在找到匹配项后继续搜索字符串。
这将在位置 0 找到 d。
现在将从位置 1 开始搜索 d,但由于这是字符串的末尾,因此它将找不到任何内容,因此返回false。
我们可以使用正则表达式的
lastIndex
属性来证明:因此,要解决该问题,您需要从正则表达式中删除
global
选项。免责声明,这是我之前答案的副本:
异常的 javascript 正则表达式结果,请解释!
Since you didn't show your RegExp but I just answered something similar to this, I suppose that you're using the
global
option in your RegExp, which has some interesting side effects.Source: https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/RegExp/test
So what exactly happens here is that since you're using the global option for the regex, it will continue to search the string after it found an match.
This will find d at position 0.
This will now search for d starting at position 1, but since that's the end of the string it will not find anything therefore returning false.
We can use the
lastIndex
property of the regex to proof that:So to solve the issue you need to remove the
global
option from your RegExp.Disclaimer, this is a copy of my previous answer:
Unusual javascript Regex result, explanation please!
这是一个棘手的问题,因为乍一看它们似乎是相同的。
我猜测 this.a 属于该函数,但也可能会延长该函数的生命周期,而不仅仅是函数调用本身;而
var a
会在每次执行函数时被创建和销毁。This is a tricky question, as at first glance they appear to be identical.
I would surmise that
this.a
is owned by the function, but may also extend for the life of that function, not just the function call itself; whereasvar a
would be created and destroyed each time the function is executed.看看此页面了解
this
的奇妙之处JS。this
的含义会发生很大的变化,具体取决于您如何使用函数。Have a look at this page about the wonders of
this
in JS. The meaning ofthis
changes quite dramatically, depending on how you use your functions.