recursion - 递归 Flatten 函数的 TypeScript 签名

标签 recursion typescript

我正在为 reactive-coffee ( http://yang.github.io/reactive-coffee/api.html ) 构建一个 Typescript .ds 文件,但在尝试找出 flatten 函数的类型签名时遇到了麻烦。一个例子:

flatten(rx.array([1, [2, 3], rx.cell(4), rx.array([rx.cell([5, rx.cell(6)])])])) 
// -> [1,2,3,4,5,6]
flatten([1, [2, 3], rx.cell(4), rx.array([rx.cell([5, rx.cell(6)])])]) 
// -> [1,2,3,4,5,6]

我遇到的问题是:xs 的正确 Typescript 类型签名是什么?到目前为止,我想出了这样的事情:

interface NestableCell<T> extends ObsCellInterface<T | NestableCell<T>> {}

type Flattenable<T> = (
    Array<T| NestableCell<T | Flattenable<T>> | Flattenable<T>> |
    ObsArrayInterface<T | NestableCell<T | Flattenable<T>> | Flattenable<T>>
)

function flatten<T>(xs:Flattenable<T>) => ObsArrayInterface<T>

ObsCellInterfaceObsArrayInterface 分别是 RC 的 ObsCellObsArray 对象的类型化版本。

不幸的是,Typescript 不允许递归类型,只允许递归接口(interface)。在这一点上,我真的不确定如何将该类型转换为接口(interface)。

最佳答案

以下似乎可行,但我还没有时间证明它满足所有可能的情况:

interface NestableCell<T> extends ObsCell<T | NestableCell<T>> {}

interface FlattenableRX<T> extends ObsArray<
    T |
    NestableCell<T | FlattenableJS<T> | FlattenableRX<T>> |
    FlattenableJS<T> |
    FlattenableRX<T>
> {}

interface FlattenableJS<T> extends Array<
    T |
    NestableCell<T | FlattenableJS<T> | FlattenableRX<T>> |
    FlattenableJS<T> |
    FlattenableRX<T>
> {}

export type Flattenable<T> = FlattenableRX<T> | FlattenableJS<T>

使用两个相互递归的接口(interface)似乎可以避免因必须同时支持原始数组和响应式(Reactive)数组而导致的最严重的并发症。

正如我所说,我还不能证明这是可行的,但至少看起来是合理的。

关于recursion - 递归 Flatten 函数的 TypeScript 签名,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40209284/

相关文章:

c - ARM 汇编中的递归打印 100

python - Leetcode Python 208. 实现Trie(前缀树)

typescript - cucumber 与 typescript 的正确用法?

c - 如何将一个数字的数字输出为整数,并且该数字可以精确整除另一个数字?

c++ - 为什么我的(重新)实现 strlen 是错误的?

sql - TSQL 函数递归

css - 在 typescript 中添加和删除类

typescript - 具有动态和静态属性的接口(interface)

typescript - 为什么在泛型类型上添加约束会改变推理行为?

json - 将 json 文件推送到 localStorage 数组中