JavaScript static 关键字是干嘛的?

2,346 阅读2分钟

image.png

JavaScript static 关键字是干嘛的?

  • 先不管他是干嘛的,先来看下面的代码 (观察现象,找规律) doge

  • 先看代码,先看带 static 关键字带情况

    class Person {
        static say () {
            return 'person say something !'
        }
    }
    
    console.log(
        Person.say
        // Person.say()
        // new Person().say
        // new Person().say()
    )
    
    • 测试一:执行 Person.say 代码

      > node b.js
      
      [Function: say]        // 得到这个结果说明,node.js 能找得到 `say函数` 的引用
      
    • 测试二:执行 Person.say() 代码

      > node b.js
      
      person say something !   // 代码正确执行
      
    • 测试三:执行 new Person().say 代码

      > node b.js
      
      undefined                // 实例中 找不到 say函数
      
    • 测试四:执行 new Person().say() 代码

      > node b.js
      
      /Users/Documents/code/src/import_export/b.js:21
          new Person().say()
                   ^
      
      TypeError: (intermediate value).say is not a function
          at Object.<anonymous> (/Users/Documents/code/src/import_export/b.js:21:18)
          at Module._compile (module.js:653:30)
          at Object.Module._extensions..js (module.js:664:10)
          at Module.load (module.js:566:32)
          at tryModuleLoad (module.js:506:12)
          at Function.Module._load (module.js:498:3)
          at Function.Module.runMain (module.js:694:10)
          at startup (bootstrap_node.js:204:16)
          at bootstrap_node.js:625:3
      
      • 直接报错! 当带有 static 的时候, 不能 new Person().say() 这么使用

  • 下面再来看一下,不带 static 关键字的情况

    • 先看代码

      class Person {
          say () {
              return 'person say something !'
          }
      }
      
      console.log(
          Person.say
          // Person.say()
          // new Person().say
          // new Person().say()
      )
      
    • 测试一:执行 Person.say 代码

      
      undefined           // 找不到
      
    • 测试二:执行 Person.say() 代码

      > node b.js 
      
      /Users/Documents/code/src/import_export/b.js:19
          Person.say()
                 ^
      
      TypeError: Person.say is not a function
          at Object.<anonymous> (/Users/Documents/code/src/import_export/b.js:19:12)
          at Module._compile (module.js:653:30)
          at Object.Module._extensions..js (module.js:664:10)
          at Module.load (module.js:566:32)
          at tryModuleLoad (module.js:506:12)
          at Function.Module._load (module.js:498:3)
          at Function.Module.runMain (module.js:694:10)
          at startup (bootstrap_node.js:204:16)
          at bootstrap_node.js:625:3
      
      • 直接报错! 没有 static 的时候,不能 Person.say() 这么使用
    • 测试三:执行 new Person().say 代码

      > node b.js
      
      [Function: say]             // 得到这个结果说明,node.js 能找得到 `say函数` 的引用
      
    • 测试四:执行 new Person().say() 代码

      > node b.js
      
      person say something !      // 正确执行
      
  • static 使用方法总结

    • 静态方法 应该在 没有实例化的时候调用

    • 反而言之:静态方法不能在类的实例中使用

  • static 的其它特性

    • 不需要通过实例对象,可以直接通过类来调用的方法,其中的 this 指向类本身

    class Person {
      static doSay () {
        this.say()
      }
      static say () {
        console.log('hello')
      }
    }
    Person.doSay() // hello
    
    • 复制代码静态方法可以被子类继承

    // ...
    class Sub extends Person {
    
    }
    Sub.doSay() // hello
    
    • 复制代码可以通过 super 对象访问

    // ...
    class Sub extends Person {
      static nice () {
        return super.doSay()
      }
    }
    Sub.nice() // hello
    
  • 另外

    • 我发现一个奇怪的问题:
    class ClassWithStaticMethod {
    
        static staticProperty = 'someValue';
        static staticMethod() {
          return 'static method has been called.';
        }
    
      }
    
      console.log(ClassWithStaticMethod.staticProperty);
      // output: "someValue"
      console.log(ClassWithStaticMethod.staticMethod());
      // output: "static method has been called."
    
    • 执行后,会报错,不知道为什么
    node b.js
    
    /Users/limi/Documents/code/import_export/b.js:28
        static staticProperty = 'someValue';
                              ^
    
    SyntaxError: Unexpected token =
        at createScript (vm.js:80:10)
        at Object.runInThisContext (vm.js:139:10)
        at Module._compile (module.js:617:28)
        at Object.Module._extensions..js (module.js:664:10)
        at Module.load (module.js:566:32)
        at tryModuleLoad (module.js:506:12)
        at Function.Module._load (module.js:498:3)
        at Function.Module.runMain (module.js:694:10)
        at startup (bootstrap_node.js:204:16)
        at bootstrap_node.js:625:3
    
    • 但是,这是 MDN 上的 例子: static 【MDN】

    • 有知道的大佬 求解答,难道这种写法 node.js 不支持?

    • 环境

      • macOS 10.13.4
      • node v8.17.0
  • 参考文章