如何有条件地向javascript对象文本添加属性
为了满足代码生成器的要求(具体来说是senchacmd),我正在尝试执行以下操作 这是我需要做的本质。关键因素是函数体必须以返回对象文本结束。由于生成器中的限制,我无法返回变量。那么,如果参数includeB为true,如何在下面的伪代码点添加属性“b”,而如果参数为false,则根本不添加属性。不允许ie b==未定义或b==null 也许这是不可能的如何有条件地向javascript对象文本添加属性,javascript,object,Javascript,Object,为了满足代码生成器的要求(具体来说是senchacmd),我正在尝试执行以下操作 这是我需要做的本质。关键因素是函数体必须以返回对象文本结束。由于生成器中的限制,我无法返回变量。那么,如果参数includeB为true,如何在下面的伪代码点添加属性“b”,而如果参数为false,则根本不添加属性。不允许ie b==未定义或b==null 也许这是不可能的 function create(includeB) { // Can have code here but the final
function create(includeB) {
// Can have code here but the final thing MUST be a return of the literal.
// ...
return {
a : 1
// pseudo code:
// if (includeB==true) then create a property called b
// and assign a value of 2 to it.
// Must be done right here within this object literal
}
}
var obj = create(false);
// obj must have property 'a' ONLY
var obj = create(true);
// obj must have properties 'a' and 'b'
感谢您的阅读和思考
Murray您可以稍后定义它:
var hasA = create(); // has hasA.a
var hasBoth = create();
hasBoth.b = 2; //now has both
或者,在create
中使用您的参数:
function create (includeB) {
var obj = {
a : 1
};
if (includeB) {
obj.b = 2;
}
return obj;
}
不能将布尔逻辑放入javascript文本定义中。因此,如果构建器要求返回的对象只能定义为javascript文本,则不能以这种方式有条件地定义属性
如果您可以在函数中创建一个对象,使用逻辑修改该对象,然后返回该对象,那么这非常简单
function create(includeB) {
var x = {
a: 1
};
if (includeB) {
x.b = 2;
}
return x;
}
您的另一个选项是包装create函数,并在create函数之外执行它
function myCreate(includeB) {
var x = create(includeB)
if (includeB) {
x.b = 2;
}
return x;
}
或者,您甚至可以透明地包装create函数,以便调用方仍然使用
create()
,但它的行为已经改变
var oldCreate = create;
create = function(includeB) {
var x = oldCreate(includeB);
if (includeB) {
x.b = 2;
}
return x;
}
这个怎么样:
function create(includeB) {
return includeB && { a:1, b:2 } || { a:1 };
}
当includeB
为true时,create函数将返回{a:1,b:2}
。如果includeB
为false,它将返回或
之后的任何内容-在这种情况下,返回{a:1}
对象
create(true)
返回{a:1,b:2}
create(false)
返回{a:1}
您已经展示了一个构造函数的用例,而不是使用对象文本:
function CustomObject(includeB) {
this.a = 1;
if (includeB) {
this.b = 2;
}
}
//has `a` only
var obj1 = new CustomObject(false);
//has `a` and `b`
var obj2 = new CustomObject(true);
在重新阅读您的问题后,似乎您在修改函数方面的权限有限。如果我正确理解您的问题,您只能更改脚本的有限部分:
function create(includeB) {
// modifications may be done here
// the rest may not change
return {
a : 1
}
}
var obj = create(false);
// obj must have property 'a' ONLY
var obj = create(true);
// obj must have properties 'a' and 'b'
如果是这种情况,您可以跳过函数的后面部分:
function create(includeB) {
if (includeB) {
return {
a: 1,
b: 2
};
}
return {
a: 1
};
}
下面的方法应该有效。我希望这有帮助 函数创建(includeB){
}如果您想使用声明一次满足相同的要求,而不需要太多膨胀,您也可以简单地执行以下操作:
var created = function(includeB) {
var returnObj = { a : 1 };
if(includeB) { returnObj.b = 2; }
return returnObj;
}}(); //automatically runs and assigns returnObj to created
这应该正是您想要的工作方式:
const obj = {
a: 1,
b: includeB ? 2 : undefined
}
我最近不得不这样做,发现可以在对象定义中使用自调用函数(如果使用ES6)。这与公认的答案类似,但对于其他需要在不首先定义构造函数的情况下执行此操作的人来说可能很有用
function myCreate(includeB) {
var x = create(includeB)
if (includeB) {
x.b = 2;
}
return x;
}
例如:
let obj = (() => {
let props = { a: 1 };
if ( 1 ) props.b = 2;
return props;
})();
使对象:{a:1,b:2}
对于更复杂的对象,它非常方便,可以保持构造的连续性:
let obj = {
a: 1,
b: (() => {
let props = { b1: 1 };
if ( 1 ) props.b2 = 2;
return props;
})(),
c: 3
}
使对象:
{
a: 1,
b: {
b1: 1,
b2: 2
},
c: 3
}
如果可以使用ES6,请使用
是的,通常我会这么做。正如我所说,在这种情况下,由于外部需求,我不能这样做,因为代码生成器基本上正在使用create函数的结果,所以我没有访问它的权限。如果可能的话,必须在伪代码所在的位置执行。@Murrah您将无法在对象中执行此操作。也许你可以在我的回答中尝试选项1?@Murrah:对象文字有一个非常特殊的语法。此语法不提供任何条件设置属性的方法。您可以将b设置为返回2或未定义的@MurrahCorrect@zzzzBov的函数,但它是一个选项。老实说,问题中给出的例子似乎不足以解决OP试图解决的任何实际问题。谢谢。是的,它必须在文本中完成。我想我可能要求的太多了@Murrah-我又添加了两个选项,让您包装create函数,并在现有的
create()
函数之外添加逻辑。谢谢。同样,特定情况下的生成器要求是,无论我给它什么函数,它都必须具有文本返回。返回x;在特定情况下是“非法的”。@Murrah-我的前两个建议没有修改实际的create()
函数。它可以保持原样而不使用.b
属性。我建议您如何添加一些简单的javascript来包装或修改create()
函数,使其按照您想要的方式运行。你不能给你的项目添加常规的javascript吗?我想你在寻找三元符号:条件?真:假;我不确定这个符号叫什么,但它似乎符合OP的要求。我猜它是另一个三元符号。我希望它返回布尔值或对象。是什么阻止您更改函数返回的对象?这看起来像是一个我没有权限访问的文件。构建器正在使用Java应用程序(Sencha Cmd)从文件系统读取JS。所提供的函数是一个测试用例,因为试图演示完整的真实情况会太令人困惑。测试用例是问题的本质。可能重复的可能重复的感谢。同上,不能返回对象,必须是文字。确定。抱歉耽搁了。我正在用构建器在真实应用程序中测试此解决方案。对生成器可以接受此语法。我以前尝试过使用“else”块,但不想尝试简单的返回。非常感谢。明确地说,这是使构建器满意的语法:函数create(includeB){if(includeB){return{a:1,b:2};}return{a:1};}在许多情况下这是优雅的语法,但需要对象Rest/Spread,目前(2017年10月29日)只是未来ECMAScript版本的第3阶段提案;不过,可以很好地使用Babel的转换。您甚至可以编写…(includeB&&{b:2})
No,这将添加属性b
,该属性将具有值unde
function create(includeB) {
return {
a : 1,
...(includeB ? { b: 2 } : {}),
};
}