首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Typescript /类型安全的库函数

Typescript /类型安全的库函数
EN

Stack Overflow用户
提问于 2020-02-13 16:05:16
回答 2查看 105关注 0票数 3

如何在typescript中安全地键入curried函数?特别是关于以下示例

代码语言:javascript
复制
interface Prop {
    <T, K extends keyof T>(name: K, object: T): T[K];
    <K>(name: K): <T>(object: T) => /* ?? */;
}

const prop: Prop = (key, object) => object[key];

const valid1 = prop('foo', { foo: 'hello' }); // string
const valid = prop('foo')({ foo: 'hello' });  // string

// `never`, since `baz` does not exist in { foo: string }
const invalid = prop('baz')({ foo: 'hello' }); // never
EN

回答 2

Stack Overflow用户

发布于 2020-02-13 17:44:00

function overload

代码语言:javascript
复制
function prop<T, K extends keyof T>(name: K, obj: T): T[K]
function prop<K extends PropertyKey>(name: K):
    <T extends Record<K, unknown>>(obj: T) => T[K]
function prop(name: any, obj?: any) { 
    if (obj === undefined) {
        return (obj: any) => obj[name]
    } else {
        return obj[name]
    }
}
// weak types used in impl for simplicity, as they don't matter for the caller.
// also this function body is not really complex
代码语言:javascript
复制
const valid1 = prop('foo', { foo: 'hello1' }); // string
const valid2 = prop('foo')({ foo: 'hello2' });  // string
const invalid = prop('baz')({ foo: 'hello' }); // compile error, `baz` not in { foo: string } 

Sample

function type

代码语言:javascript
复制
interface Prop {
    <T, K extends keyof T>(name: K, obj: T): T[K];
    <K extends PropertyKey>(name: K): <T extends Record<K, unknown>>(obj: T) => T[K]
}

const prop: Prop = (name: any, obj?: any) => {
    if (obj === undefined) {
        return (obj: any) => obj[name]
    } else {
        return obj[name]
    }
}
// weak types used here for simplicity like in first solution
代码语言:javascript
复制
const valid1 = prop('foo', { foo: 'hello1' }); // string
const valid2 = prop('foo')({ foo: 'hello2' });  // string
const invalid = prop('baz')({ foo: 'hello' }); // never
console.log(valid1, valid2) // hello1 hello2

Sample

注意:函数重载和函数类型不能完全互换使用(更多信息是herehere)。对于后者,可能需要在函数实现部分使用any注释类型,以说明定义的调用签名中不兼容的返回类型-查看此playground以获取示例。

票数 3
EN

Stack Overflow用户

发布于 2020-02-15 03:44:46

可能有点冗长,但做了它需要做的事情:

代码语言:javascript
复制
interface Prop {
    <K extends PropertyKey, T extends {}>(name: K, object: T): K extends keyof T ? T[K] : undefined;
    <K extends PropertyKey>(name: K): <T extends {}>(object: T) => K extends keyof T ? T[K] : undefined;
}

declare const prop: Prop;

const invalid = prop('bar')({ foo: 'hello world' });
const valid = prop('foo')({ foo: 'hello world' });
const sLen = prop('length', 'Hello World');
const arity = prop('length')((a: number, b: number, c: number) => a + b + c);
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/60203078

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档