microsoft / microsoft/TypeScript
Alternate syntax for function overloads
まだ誰も着手していません。
- 主要言語
- Go
- スター
- 111k
- フォーク
- 14.3k
- 平均マージ
- 2日 4時間
- マージ済み PR(30日)
- 132
説明
Search Terms
class method signature
method signature
function overload syntax
function overload
proxy function
proxy function signature
Suggestion
A new syntax for function overloads:
function Func as FunctionSignature
class A {
static Func as FunctionSignature
Func as FunctionSignature
}
This would allow types to be less static, and often more accurate to the purpose of the overloaded function
Right now, we can do something similar using const -
const: FunctionSignature = function() {}
however, the differences in detailed in #25761 and the lack of any equivalent in classes make this a separate issue.
I'm not dead set on the as syntax, but I think it fits with what we already have quite well. The checking done on overloads is similar to that of ({ prop: "HI" } as { prop: number }), and it fits well in and out of classes
It's also worth noting that every use case of this would benefit greatly from #28172
Use Cases
Generic Types
type Pipe<V> = (val: V) => V
function MyFunc as Pipe<string>
// function MyFunc(val: string): string
function MyFunc(...args: any[]): any {
}
Inheritance
function tryInt as typeof parseInt
// function tryInt(s: string, radix?: number): number
function tryInt(...args: [string, number?]) {
const n = parseInt(...args)
if (isNaN(n)) throw "Failed to parse"
return n
}
Combining function implementations
A solution to the problems brought up in #12041 -
function overload as typeof implementation
function overload as typeof otherImplementation
// function overload(num: number): string
// function overload(str: string, num: number): string
function overload(...args: [string, number] | [number]) {
return args.length === 1 ? implementation(...args) : otherImplementation(...args)
}
Which would work particularly well combined with #28172,
function overload as typeof implementation
function overload as typeof otherImplementation
function overload() {
return arguments.length === 1 ? implementation(...arguments) : otherImplementation(...arguments)
}
fully checking the types against the current signature of both implementations, and emitting useful errors
Examples
This came up in the context of an argument parser, where I attempt to parse the values using a direct proxy to another method -
class ArgumentIssue {
confidence: number
}
class Arguments {
async parse(args: string, cb: (val: string) => any = v => v): Promise<{ [key: string]: any }> {
// Follows the return value ^
}
}
class Signature extends Array<Arguments> {
parse as ArgumentBuilder["parse"]
// parse(args: string, cb: (val: string) => any): Promise<{ [key: string]: any }>
parse(a: any, ...args: any[]) {
let Nearest: [Arguments, ArgumentIssue];
for (const overload of this) {
try {
return overload.parse(a, ...args)
} catch (issue) {
if (!(issue instanceof ArgumentIssue)) throw issue;
if (!Nearest || issue.confidence > Nearest[1].confidence)
Nearest = [overload, issue];
}
}
throw Nearest;
}
}
Checklist
My suggestion meets these guidelines:
- This wouldn't be a breaking change in existing TypeScript/JavaScript code
- This wouldn't change the runtime behavior of existing JavaScript code
- This could be implemented without emitting different JS based on the types of the expressions
- This isn't a runtime feature (e.g. library functionality, non-ECMAScript syntax with JavaScript output, etc.)
- This feature would agree with the rest of TypeScript's Design Goals.
コントリビューションガイド
はじめの一歩
- issue を最後まで読み、次にプロジェクトのコントリビューションガイドを読みます。
- 着手することを issue にコメントします — 二人が同じ作業をするのを防げます。
- リポジトリをフォークし、ブランチを切って変更します。
- issue 番号を参照したプルリクエストを送ります。
調査の方向性
この issue では関数とクラスのオーバーロード用の新しい構文が提案されていますが、ファイル、テスト、エントリーポイントは指定されていません。まず、提案された宣言を既存のオーバーロードおよび #25761 の const ベースのアプローチと比較し、その後 #12041 と #28172 の関連する議論を確認してください。type checker 向けの承認済みの設計と実装計画がまとまれば完了です。
索引モデルが issue の本文から書いたものです。
評価
- 技術スタック
- typescript
- 領域
- compilers
- issue の種類
- 機能追加
- 難易度
- 5/5
- 見積もり時間
- 1週間以上
- 活発さ
- 停滞
- 明瞭さ
- おおむね明確
- 初心者へのやさしさ
- 25/100