gpt4 book ai didi

JavaScript,定义不可修改的枚举

转载 作者:行者123 更新时间:2023-12-02 18:18:49 24 4
gpt4 key购买 nike

因此,我受到这个问题 ( Enums in JavaScript? ) 的启发,开始为 JavaScript 开发库插入以启用不可修改的枚举。我已经定义了一个不错的工作方法,但我想进一步充实它。

这个概念利用了Object.defineProperty(文档:Here)

我当前的定义允许:

var obj1 = {}, obj2 = {}, obj3 = {};
// Straight declaration (normal)
obj1.Enum('RED','BLUE','GREEN');
obj1.RED // == 0
obj1.BLUE // == 1
obj1.GREEN // == 2
// Buffer (padding) usage
obj2.Enum('RED','BLUE',null,undefined,'','GREEN');
obj2.RED // == 0
obj2.BLUE // == 1
obj2.GREEN // == 5
// Direct offset and case-correction
obj3.Enum('RED','BLUE',10,'gReEn','burnt orange');
obj3.RED // == 0
obj3.BLUE // == 1
obj3.GREEN // == 11
obj3.BURNT_ORANGE // == 12

到目前为止我所拥有的:

var odp=Object.defineProperty;
odp(Object.prototype,'Enum', {
value: function() {
var ignore=[undefined,null,''], n=0, args=arguments;
for(var i in args) {
if(ignore.indexOf(args[i])<0) {
if( typeof args[i]=="number") {
n=parseInt(args[i]);
} else {
try {
odp(this,String(args[i]).toUpperCase().replace(" ","_"), {
value:parseInt(n),enumerable:true
});
} catch(e) {
console.warn(e.message);
n--;
}
}
}
n++;
}
return this;
}
});

我想添加的两件事是:

  1. 旧版浏览器支持:因此,在未定义的地方重新定义Object.defineProperty。 (我目前无法访问旧版浏览器来测试可能的重新定义)
  2. 我可能忽略了 Enum 定义的任何注意事项。

jsFiddle:

注意: 我拥有 odp=Object.definePropertyargs=arguments 的原因是我之前通过闭包编译器运行 JavaScript将其插入我的页面中,这样做有助于压缩。 (对于那些可能想知道的人)

最佳答案

Older browser support: So, redefining Object.defineProperty where it's not defined.

您当前的方法无法做到这一点,因为您当前的方法扩展了 Object.prototype。如果您有 ES5 支持,则扩展 Object.prototype 应该非常非常少,但如果没有它,则绝不能这样做,因为没有 Object.defineProperty,你没有办法创建一个不可枚举的属性。向 Object.property 添加可枚举属性将破坏所有 for-in 循环。

无论如何,Enum 没有理由出现在原型(prototype)上,只需将其放在 Object (或您自己的库对象)上并将该对象传递为枚举即可-化为它。

Any considerations I may have missed it the Enum definition.

在我看来,这几乎没有提供:

var obj = Object.freeze({
"RED": 0,
"GREEN": 1,
"BLUE": 2
});

您可以将其包装到一个可以在 ES5 之前的环境中运行的函数中,而无需卡住对象,例如:

function createEnum(spec) {
if (Object.freeze) {
spec = Object.freeze(spec);
}
return spec;
}

当然,如果您想要自动值,您可以增强它,例如:

function createEnum(spec) {
var obj = {}, n;
if (Object.prototype.toString.call(spec) === "[object Array]") { // No isArray pre ES5
for (n = 0; n < spec.length; ++n) {
if (spec[n] != null) { // checks for null or undefined
obj[spec[n]] = n;
}
}
}
else {
for (n in spec) {
if (spec.hasOwnProperty(n)) {
obj[n] = spec[n];
}
}
}
if (Object.freeze) {
obj = Object.freeze(obj);
}
return obj;
}

如果您愿意,您可以将其放在 Object 上(不是 Object.prototype)。

<小时/>

下面您已经说过您不想使用freeze,因为它会使对象不可扩展。很公平,希望稍后添加更多枚举值。上面的内容很容易适应这一点,如果存在的话使用 Object.defineProperty ,如果不存在则仅分配属性。

关于JavaScript,定义不可修改的枚举,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19035446/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com