Skip to content

Commit 98523b4

Browse files
committed
Support multiplication operator for type params.
1 parent 11fdd96 commit 98523b4

File tree

3 files changed

+61
-4
lines changed

3 files changed

+61
-4
lines changed

compiler/expressions.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -690,6 +690,8 @@ func (fc *funcContext) translateBinaryExpr(e *ast.BinaryExpr) *expression {
690690
return fc.formatExpr("%s.add(%e, %e)", fc.typeName(t), e.X, e.Y)
691691
case token.SUB:
692692
return fc.formatExpr("%s.sub(%e, %e)", fc.typeName(t), e.X, e.Y)
693+
case token.MUL:
694+
return fc.formatExpr("%s.mul(%e, %e)", fc.typeName(t), e.X, e.Y)
693695
}
694696
}
695697

compiler/prelude/types.js

Lines changed: 15 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -418,29 +418,40 @@ var $newType = (size, kind, string, named, pkg, exported, constructor) => {
418418
// This methods will be called when the exact type is not known at code generation time, for
419419
// example, when operands are type parameters.
420420
switch (kind) {
421-
case $kindInt:
422421
case $kindInt8:
423422
case $kindInt16:
424-
case $kindInt32:
425423
case $kindUint:
426424
case $kindUint8:
427425
case $kindUint16:
428-
case $kindUint32:
429-
case $kindUintptr:
430426
case $kindFloat32:
431427
case $kindFloat64:
432428
typ.add = (x, y) => $truncateNumber(x + y, typ);
433429
typ.sub = (x, y) => $truncateNumber(x - y, typ);
430+
typ.mul = (x, y) => $truncateNumber(x * y, typ);
431+
break;
432+
case $kindUint32:
433+
case $kindUintptr:
434+
typ.add = (x, y) => $truncateNumber(x + y, typ);
435+
typ.sub = (x, y) => $truncateNumber(x - y, typ);
436+
typ.mul = (x, y) => $imul(x, y) >>> 0;
437+
break;
438+
case $kindInt:
439+
case $kindInt32:
440+
typ.add = (x, y) => $truncateNumber(x + y, typ);
441+
typ.sub = (x, y) => $truncateNumber(x - y, typ);
442+
typ.mul = (x, y) => $imul(x, y);
434443
break;
435444
case $kindInt64:
436445
case $kindUint64:
437446
typ.add = (x, y) => new typ(x.$high + y.$high, x.$low + y.$low);
438447
typ.sub = (x, y) => new typ(x.$high - y.$high, x.$low - y.$low);
448+
typ.mul = (x, y) => $mul64(x, y);
439449
break;
440450
case $kindComplex64:
441451
case $kindComplex128:
442452
typ.add = (x, y) => new typ(x.$real + y.$real, x.$imag + y.$imag);
443453
typ.sub = (x, y) => new typ(x.$real - y.$real, x.$imag - y.$imag);
454+
typ.mul = (x, y) => new typ(x.$real * y.$real - x.$imag * y.$imag, x.$real * y.$imag + x.$imag * y.$real);
444455
break;
445456
case $kindString:
446457
typ.add = (x, y) => x + y;

tests/typeparams/arithmetics_test.go

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -120,3 +120,47 @@ func TestSubtract(t *testing.T) {
120120
t.Run(test.String(), test.Run)
121121
}
122122
}
123+
124+
type muiltipliable interface {
125+
constraints.Integer | constraints.Float | constraints.Complex
126+
}
127+
128+
func mul[T muiltipliable](x, y T) T {
129+
return x * y
130+
}
131+
132+
func mulTC[T muiltipliable](x, y, want T) *testCase[T] {
133+
return &testCase[T]{
134+
op: mul[T],
135+
opName: token.MUL,
136+
x: x,
137+
y: y,
138+
want: want,
139+
}
140+
}
141+
142+
func TestMul(t *testing.T) {
143+
tests := []testCaseI{
144+
mulTC[int](2, 3, 6),
145+
mulTC[uint](2, 3, 6),
146+
mulTC[uintptr](2, 3, 6),
147+
mulTC[int8](2, 3, 6),
148+
mulTC[int16](2, 3, 6),
149+
mulTC[int32](2, 3, 6),
150+
mulTC[uint8](2, 3, 6),
151+
mulTC[uint16](2, 3, 6),
152+
mulTC[uint32](2, 3, 6),
153+
mulTC[int8](127, 3, 125), // Overflow.
154+
mulTC[uint8](250, 3, 238), // Overflow.
155+
mulTC[float32](2.5, 1.4, 3.5),
156+
mulTC[float64](2.5, 1.4, 3.5),
157+
mulTC[int64](0x0000003200000001, 0x0000000100000002, 0x0000006500000002),
158+
mulTC[uint64](0x0000003200000001, 0x0000000100000002, 0x0000006500000002),
159+
mulTC[complex64](1+2i, 3+4i, -5+10i),
160+
mulTC[complex128](1+2i, 3+4i, -5+10i),
161+
}
162+
163+
for _, test := range tests {
164+
t.Run(test.String(), test.Run)
165+
}
166+
}

0 commit comments

Comments
 (0)