Javascript中是否有空合并运算符?
例如,在C#中,我可以这样做:
String someString = null; var whatIWant = someString ?? "Cookies!";
我可以为Javascript找出的最佳近似值是使用条件运算符:
var someString = null; var whatIWant = someString ? someString : 'Cookies!';
这有点ick嘿恕我直言.我可以做得更好吗?
C#null coalescing operator(??
)的JavaScript等价物使用逻辑OR(||
):
var whatIWant = someString || "Cookies!";
有些情况(下面说明)表明行为与C#的行为不匹配,但这是在JavaScript中分配默认/替代值的一般,简洁的方法.
无论第一个操作数的类型如何,如果将其转换为布尔值false
,则赋值将使用第二个操作数.请注意以下所有情况:
alert(Boolean(null)); // false alert(Boolean(undefined)); // false alert(Boolean(0)); // false alert(Boolean("")); // false alert(Boolean("false")); // true -- gotcha! :)
这意味着:
var whatIWant = null || new ShinyObject(); // is a new shiny object var whatIWant = undefined || "well defined"; // is "well defined" var whatIWant = 0 || 42; // is 42 var whatIWant = "" || "a million bucks"; // is "a million bucks" var whatIWant = "false" || "no way"; // is "false"
function coalesce() { var len = arguments.length; for (var i=0; i此解决方案的工作方式类似于SQL coalesce函数,它接受任意数量的参数,如果它们都没有值,则返回null.它的行为就像C#?? 运算符,"",false和0被认为是NOT NULL,因此计为实际值.如果你来自.net背景,这将是最自然的感觉解决方案.
对这种后期添加表示歉意,但我只想注意完整性,这个解决方案确实有一个警告,即它没有短路评估; 如果你的参数是函数调用,那么无论它们的值是否返回,它们都将被评估**,这与逻辑OR运算符的行为不同,因此值得注意.
根据[MDN](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/for ..),`for(var i in arguments)`不保证迭代顺序. .在#Array_iteration_and_for ...的).另请参阅[为什么JavaScript的For ...循环不推荐用于数组?](http://stackoverflow.com/q/5269757/1468366)和[为什么在数组迭代中使用"for ... in"这么糟糕的主意?] (http://stackoverflow.com/q/500504/1468366).
3> sth..:如果
||
作为C#的替换??
在你的情况下不够好,因为它吞下空字符串和零,你总是可以编写自己的函数:function $N(value, ifnull) { if (value === null || value === undefined) return ifnull; return value; } var whatIWant = $N(someString, 'Cookies!');
4> vaughan..:是的,它即将推出.在此处查看提案和实施状态.
它看起来像这样:
x ?? y例
const response = { settings: { nullValue: null, height: 400, animationDuration: 0, headerText: '', showSplashScreen: false } }; const undefinedValue = response.settings?.undefinedValue ?? 'some other default'; // result: 'some other default' const nullValue = response.settings?.nullValue ?? 'some other default'; // result: 'some other default' const headerText = response.settings?.headerText ?? 'Hello, world!'; // result: '' const animationDuration = response.settings?.animationDuration ?? 300; // result: 0 const showSplashScreen = response.settings?.showSplashScreen ?? true; // result: false
现在处于第3阶段,并计划用于下一个TypeScript版本!https://github.com/microsoft/TypeScript/issues/26578
5> Kevin Nelson..:在这里没有人提到潜力
NaN
,对我来说,这也是一个无效的价值.所以,我以为我会增加两美分.对于给定的代码:
var a, b = null, c = parseInt('Not a number'), d = 0, e = '', f = 1 ;如果您要使用
||
运算符,则会获得第一个非假值:var result = a || b || c || d || e || f; // result === 1如果您使用典型的合并方法,如此处发布,您将获得
c
,其值为:NaN
var result = coalesce(a,b,c,d,e,f); // result.toString() === 'NaN'这些似乎都不适合我.在我自己的小合并逻辑世界中,可能与你的世界不同,我认为undefined,null和NaN都是"null-ish".所以,我希望
d
从coalesce方法中恢复(零).如果任何人的大脑像我一样工作,并且你想要排除
NaN
,那么这种方法将实现:function coalesce() { var i, undefined, arg; for( i=0; i < arguments.length; i++ ) { arg = arguments[i]; if( arg !== null && arg !== undefined && (typeof arg !== 'number' || arg.toString() !== 'NaN') ) { return arg; } } return null; }对于那些希望代码尽可能短,并且不介意有点缺乏清晰度的人,你也可以按照@impinball的建议使用它.这利用了NaN永远不等于NaN的事实.你可以在这里阅读更多内容:为什么NaN不等于NaN?
function coalesce() { var i, arg; for( i=0; i < arguments.length; i++ ) { arg = arguments[i]; if( arg != null && arg === arg ) { //arg === arg is false for NaN return arg; } } return null; }
@impinball,我在建议的编辑中找到了您的错误,您将其保留为arg!== arg,但您需要将其设为arg === arg ...然后它可以工作。但是,这样做的缺点是不清楚您在做什么……需要在代码中添加注释,以防止被下一个经过代码并认为arg === arg的人删除。但我还是把它放起来。
6> Elmar Jansen..:目前没有支持,但JS标准化过程正在努力:https://github.com/tc39/proposal-optional-chaining
这有点不同:a .b(如果存在则访问ab),而不是?? b(如果存在,则a,否则b).
7> farzad..:当心JavaScript的null定义。在javascript中,“ no value”有两个定义。1. Null:当变量为null时,表示它不包含任何数据,但是该变量已在代码中定义。像这样:
var myEmptyValue = 1; myEmptyValue = null; if ( myEmptyValue === null ) { window.alert('it is null'); } // alerts在这种情况下,变量的类型实际上是对象。测试一下。
window.alert(typeof myEmptyValue); // prints Object
未定义:如果之前未在代码中定义变量,并且不出所料,则该变量不包含任何值。像这样:
if ( myUndefinedValue === undefined ) { window.alert('it is undefined'); } // alerts在这种情况下,变量的类型为“未定义”。
请注意,如果您使用类型转换比较运算符(==),则JavaScript将对这两个空值均起同样的作用。为了区分它们,请始终使用类型严格的比较运算符(===)。