ecmascript-types icon indicating copy to clipboard operation
ecmascript-types copied to clipboard

Allow overloading functions by return type

Open sirisian opened this issue 3 years ago • 0 comments

This apparently had performance concerns in early programming languages, but a few languages have implemented it including Swift and Haskell(?).

function F():uint32 {
  return 10;
}
function F():string {
  return "10";
}
// F(); // TypeError: Ambiguous signature for F. Requires explicit left-hand side type.
const a:string = F(); // "10"
const b:uint32 = F(); // 10

function G(a:uint32) {
  return a;
}
G(F()); // 10

function H(a:uint8) { }
function H(a:string) { }
// H(F()); // TypeError: Ambiguous signature for F. Requires explicit left-hand side type.

It's possible for an engine to have type inference that supports:

const a = F();
G(a); // a must be uint8, thus F():uint8 is the only valid signature.

To what extent should this inference be supported?

Why even support such a complex language feature?

In other languages you'll have people write getString() and getUInt8() or if they support generics get<string>() and get<uint8>(). This seems fine at first glance until you think about operators. Take SIMD operators, represented here by their intrinsic, that can return both a vector register or mask:

__m128i _mm_cmpeq_epi32 (__m128i a, __m128i b)
__mmask8 _mm_cmpeq_epi32_mask (__m128i a, __m128i b)

Notice Intel differentiates signatures by adding _mask. When translated to real types with operators they are identical however:

const something = int32x4(0, 1, 2, 3) < int32x4(0, 1, 3, 2);

But if we overload return types we can support both signatures:

const a:int32x4 = int32x4(0, 1, 2, 3) == int32x4(0, 1, 3, 2);
const b:boolean8 = int32x4(0, 1, 2, 3) == int32x4(0, 1, 3, 2);

sirisian avatar Dec 05 '22 03:12 sirisian