对所有永远不会改变的变量使用const是否有意义?

时间:2015-10-23 06:02:57

标签: ecmascript-6 const

考虑到这样的事情:

const

这是否过度使用let?我应该在这里使用`id parentClass = [self.view parentViewController]; ` and then try with `if([parentClass isKindOfClass[ViewController1 Class]]){ // view 1 } else if ([parentClass isKindOfClass[ViewController2 Class]]) { // view 2 } else if ([parentClass isKindOfClass[ViewController3 Class]]) { // view 3 } ` 吗?

3 个答案:

答案 0 :(得分:5)

const的使用取决于个人。如果你假装javascript是强类型的,那么大多数javascript引擎的优化效果最好。因此,const似乎是一个好主意。

一些事实。

  • MDN声明,consts的块范围与let类似。这是真的 严格模式。
  • 必须为声明分配一个值。只有严格要求 模式。
  • 无法重新分配Consts。严格和正常都是如此 但在正常的javascript中,分配给一个常量会无声地失败 代表难以发现的错误的来源。 (注意没有好处 不使用严格模式的论据)

差异作为例子

function log(d){console.log(d);}
(function (){
    if(true){
        const a = 10;  // correctly formed use of constant
        const b;       // does not fail
        log(a);        // 10;
        log(b);        // undefined
        b = 10;        // nothing happens. If you have forgoten this is a constant
                       // you will have a hard time knowing this assignment is failing
        log(b);        // undefined
    }
    // scope not respected
    log(a); // 10 const should have block scope. This does not seem to be true
            // in normal javascript
})();

// function in strict mode
// not this is an example only and can not run. It is a compilation of several functions
(function (){
    "use strict";
    if(true){
        const a = 10;    
        const b;     // SyntaxError: Unexpected token. Javascript parsing 
                     // stops here and the function will never be called
        a = 20;      // TypeError: Assignment to constant variable
    }
    // scope is respected
    log(a); // ReferenceError: a is not defined
})();

正如您所看到的,在严格模式下使用const之间存在很大差异。除了严格的模式之外,在任何东西中使用常量都是蛮干的。

性能。 Chrome在采用const时已经很早了,至少3年前我记得使用const。由于我专注于图形,因此性能至关重要。我推断const将提供急需的性能优势,就像#define在C / C ++中通过简单代码插入常量值一样。可悲的是,到那天结束时,我完全反对使用const,因为它表现糟糕。

此后它有所改善。

jsperf "Consts V Vars"

在所有测试中,使用const的速度始终较慢,但它很小,而且距离调用太近。唯一的例外是块范围声明,它大约是varlet速度的1/3。一个令人惊讶的发现是let现在在Chrome Beta上非常快,一个月前我不会接近它,这是我回答的原因。

OP问道...... 对所有永远不会改变的变量使用const是否有意义?

一年前,我会说"永远不要使用它"。几个月前我会说,"有充分的理由,但var更好"。

现在我的答案肯定是使用常量,只要你想要一个变量永不改变。常量输出执行文字,并且与var一样好。

const c = 10;
var v = 10;
var a = 10; // this is slower 
var a = c; // this is 20% faster
var a = v; // this is about < 1% faster than const.

根据浏览器所经历的变化率,以及Chrome上letconst的最近几个月的效果变化。我怀疑常数将在今年年底之前完成变量。 (请注意我使用的是Chrome Beta 47)

我所执行的测试没有为代码优化提供太多空间,因此我猜测在使用const时还有额外的性能,这在测试中并不明显。

一个常量本质上是强类型的,这为javascript优化算法提供了一些东西来提供额外的性能。

使用常量可以提高代码质量。 Javascript(甚至是严格模式)可以长时间隐藏错误,使用常量可以降低错误分配,意外类型转换等风险。

<强> BUT 我对const的使用发出了重大警告。 仅在严格模式下使用const ,它在普通javascript中的行为很危险,只会给你带来问题。

答案 1 :(得分:2)

Blindman67从性能角度给出了一个很好的论据。由于javascript / ecmascript编译器一直在改变/改进,我会考虑从提供更多可读/可维护代码的角度更多地回答这个问题。

标记变量'const'有时很有用,表示值是不可变的。这也适用于编译器不强制执行const检查的情况 - 比如标记对象数组const仍然允许您更改该数组中对象的状态。这当然归结为团队内部的编码风格,但我发现大多数人都认为变量定义的const,即使可以改变,也是不可改变的。

这个论点的另一方面是过度使用const。当然你可以在任何地方使用const,它只会使代码更难以通过,并且更难以对其进行更改。我发现在实践中,此类代码的大多数维护工作都是从删除大多数“const”关键字开始,以便可以进行必要的额外更改。因此,虽然有很多常量,但最初看起来可能看起来很棒,但从长远来看,我认为它对可维护性几乎没有任何影响,相反,它会使维护变得更加困难。

tl; dr 使用const,您认为它会增加代码的可读性。

答案 2 :(得分:1)

我认为const关键字经常被滥用。 如果您严格要编写纯函数,则在各处都使用const是有意义的(函数编程方法) 但是如果您不想100%遵守FP宗教,那么我认为您应该只使用let。 就个人而言,我在Node.js中也将const用于诸如const MAX_HEIGHT = 1234;之类的实际常量,我认为在文件开头执行const fs = require('fs');也是有意义的。

这是理论上旨在保护开发人员免受自身侵害的功能之一,但是我不特别喜欢重构过度使用const的代码;我一直都必须一直将const变量重命名为let-如果您不小心忘记将声明更改为let,则可能会出现问题,因为在该代码路径下可能会导致错误执行。

我认为,如果您使用const,则需要确保该变量在语义上是一个常量,并且在可预见的将来将保持不变。 另外,我认为如果过度使用const有时会带来错误的安全感。例如,您可以进行const obj = {};,然后再修改对象obj.newProperty = 1234;-之所以允许这样做,是因为您没有更改对象引用本身,但看起来确实违反了const的目的。