这个问题已经存在好几年了。
我正在为名为 Discuz 的论坛引擎编写一些插件,我在自己的项目中使用了很多 Mootools。当我将Mootools插入这个论坛引擎(discuz)时,事情变得疯狂......
去年我做了一些调试后,我发现问题是Mootools原型了很多核心元素,包括Array,并且,另一方面,该论坛引擎使用大量的 For(i in Array) 循环来表示“数组”。这肯定会导致问题,因为
for(i in [1,2,3,4,5]) console.log(i); //0,1,2,3,4 the keys in this array
**WITH MOOTOOLS
for(i in [1,2,3,4,5]) console.log(i);
//OUTPUT 0,1,2,3,4,$family,$constructor,pop,push,reverse,shift,sort,splice.......
上次我使用解析器更改所有 for(i in array) 循环以添加“if item.hasOwnProperty()”来绕过这些原型
但我认为这是一个非常糟糕的解决方法,因为你知道,会导致更多问题...新版本,修改他们的代码...等等
我想知道是否有解决方法来解决这个问题?不接触任何这个论坛引擎的js代码,并且还使用Mootools?
我知道对数组使用 For(..in ) 是不好的,但我的问题是我不想接触这个论坛引擎的 javascript 代码,我只是想要一个解决方案来过载问题
This problem been there for couple years.
I am writing some plugins for a Forum engine called Discuz, I use a lot of Mootools for my own projects. When I plug Mootools into this forum Engine(discuz) things went crazy...
After I did some debugging last year, I found that the problem is that Mootools prototype a lot of core elements, including Array, And, on the other hand, this forum engine uses a lof of For(i in Array) Loop for 'array'. Which will certainly cause problem because
for(i in [1,2,3,4,5]) console.log(i); //0,1,2,3,4 the keys in this array
**WITH MOOTOOLS
for(i in [1,2,3,4,5]) console.log(i);
//OUTPUT 0,1,2,3,4,$family,$constructor,pop,push,reverse,shift,sort,splice.......
Last time i use a parser to change all for(i in array) loop to add an 'if item.hasOwnProperty()' to by pass those prototypes
But i think this is a very bad work-around cause u know, cause more problems...new versions, bug up their codes...etc
I wonder if there is work around to slove this problem? without touching any of this forum engine's js code, and also use Mootools?
I know that using For(..in ) for Array is bad, but my question is i dont want to touch this forum engine's javascript codes, i just want a solution to over load the problem
发布评论
评论(3)
正如您所提到的,您应该使用
hasOwnProperty()
。我不确定为什么您认为这会导致更多问题,实际上,对于for(x in y)
循环,我倾向于默认使用hasOwnProperty()
并且仅在特殊情况下省略它。话虽如此,我不会在数组上使用for 并在循环内测试
for(x in y)
循环。通常最好使用标准的 for(i=0; iundefined
。)更新: 好的,我现在明白了。如果您想继续使用 MooTools,那么插入
hasOwnProperty()
的解决方法是我能想到的最佳解决方案。在for
的结束)
之后插入它应该是相当安全的:您不需要检查现有的{ }
括号或添加您自己的。You should use
hasOwnProperty()
as you mentioned. I'm not sure why you think this would cause more problems, indeed with afor(x in y)
loop I'd be inclined to usehasOwnProperty()
by default and only omit it for special cases.Having said that, I wouldn't use a
for(x in y)
loop on an array. It's generally better to use a standardfor(i=0; i<y.length; i++)
loop which will of course ignore all the non-numeric properties. (Except perhaps if you know you've got non-consecutive array indexes, in which casefor(x in y)
will skip the unused indexes, but even in that case I'd probably still use a standardfor
and test forundefined
within the loop.)UPDATE: OK, I get it now. Your work-around to insert the
hasOwnProperty()
is the best solution I can think of if you want to keep using MooTools. Should be reasonably safe to insert it just after the closing)
of thefor
: you shouldn't need to check for existing{}
brackets or add your own.一些较新的浏览器支持方法来制作所有这些额外的属性(家族、构造函数等)不可枚举,因此它们不会出现在 for-in 循环中。
但是,如果您也希望能够支持旧浏览器,我认为您运气不好:for-in 是硬连线语法,因此您无法对其进行猴子修补。 (无论如何,神奇的查找替换似乎已经起作用了......)
Some newer browsers support ways to make all those extra properties (family, constructor, etc) be not enumerable, so they don't appear in the for-in loops.
However, if you want to be able to support the old browsers as well I think you are out of luck: for-in is hardwired syntax so you wont be able to monkey-patch it. (Anyway, the magic find-replace seems to have worked...)
Mootools 扩展了 Array.prototype 甚至可能是 Object.prototype,它可能会干扰 for .. in 循环,该循环枚举所有属性,甚至是那些属性存在于对象中是因为它们出现在原型链上。因此,在使用该属性之前,请测试该属性是否是对象的直接属性:
Mootools extends
Array.prototype
and maybe evenObject.prototype
, which can interfere withfor .. in
loops, which enumerate all properties, even those that exist in the object because they appear upwards on the prototype chain. Therefore, test if the property is a direct property of the object before using it: