【问题标题】:TypeScript return immutable/const/readonly ArrayTypeScript 返回不可变/常量/只读数组
【发布时间】:2018-04-24 13:36:03
【问题描述】:

我想要一个返回数组的函数,但我希望返回的数组是只读的,所以当我尝试更改其内容时应该会收到警告/错误。

function getList(): readonly number[] {
   return [1,2,3];
}


const list = getList();
list[2] = 5; // This should result in a compile error, the returned list should never be changed

这可以在 TypeScript 中实现吗?

【问题讨论】:

  • 使用Readonly<number[]> 存在一个问题。我不能再使用for...of,说该类型必须有一个返回迭代器的方法。
  • ...它doesn't seem to work。我肯定会在那里出错吗?
  • 我不认为这完全是重复的。据我所知,接受的答案甚至在其他问题中都不起作用。
  • @series0ne:是的,见上文。我去尝试了,所以我可以评论一个例子(我喜欢用傻瓜来做),然后......它没有用。 :-)
  • 在纯 JS 中,您可以使用 a => Object.freeze(a);a 数组转换为浅不可变数组。尝试更改或删除它的项目似乎会在严格模式下抛出“类型错误”,但否则会失败。如果其中任何一项是引用类型,那么它将保持可变,除非您将它们冻结,即递归。

标签: javascript typescript immutability readonly


【解决方案1】:

这似乎有效...

function getList(): ReadonlyArray<number> {
    return [1, 2, 3];
}

const list = getList();

list[0] = 3; // Index signature in type 'ReadonlyArray<number>' only permits reading.

Playground试试吧

ReadonlyArray&lt;T&gt; 是这样实现的:

interface ReadonlyArray<T> {
    readonly [n: number]: T;
    // Rest of the interface removed for brevity.
}

【讨论】:

  • 谢谢,这就是我要找的。我认为TypeScript 文档在这个方向上缺乏,没有太多引用这个功能。
【解决方案2】:

来自 OP 的代码现在可以在 TypeScript 3.4 introduced a new syntax for ReadonlyArray 之后运行:

虽然最好使用 ReadonlyArray 而不是 Array 突变是有意的,考虑到数组有一个 更好的语法。具体来说,number[]Array&lt;number&gt;,就像Date[]Array&lt;Date&gt; 的简写一样。

TypeScript 3.4 为 ReadonlyArray 引入了一种新语法,使用了新的 readonly 数组类型的修饰符。

此代码现在按预期工作:

function getList(): readonly number[] {
   return [1,2,3];
}

const list = getList();
list[2] = 5; // <-- error

Playground.

【讨论】:

    【解决方案3】:

    以下内容将使列表成为只读,但其中的项目不是:

    function getList(): Readonly<number[]> {
       return [1,2,3];
    }
    
    let list = getList();
    list = 10; // error
    list[1] = 5 // that is fine
    

    这将使列表和它的项目只读:

    function getList(): ReadonlyArray<number> {
       return [1,2,3];
    }
    
    let list = getList();
    list = 10; // error
    list[1] = 5 // error as well
    

    【讨论】:

      【解决方案4】:

      TypeScript 有一个 ReadonlyArray&lt;T&gt; 类型,可以这样做:

      TypeScript 带有与 Array 相同的 ReadonlyArray 类型,删除了所有变异方法,因此您可以确保在创建后不会更改数组

      function getList(): ReadonlyArray<number> {
         return [1,2,3];
      }
      
      const list = getList();
      list[2] = 5; // error
      
      for (const n of list) {
          console.log(n);
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2015-11-15
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2017-04-15
        • 2013-10-30
        相关资源
        最近更新 更多