JS backend: fix default arguments
generate special statements, like this:
if (arg1 === void(0))
arg1 = value1
This commit is contained in:
@@ -1,54 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2013 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.jetbrains.k2js.test.semantics;
|
||||
|
||||
import junit.framework.Test;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.k2js.test.BasicTest;
|
||||
import org.jetbrains.k2js.test.SingleFileTranslationTest;
|
||||
import org.jetbrains.k2js.translate.context.Namer;
|
||||
|
||||
@SuppressWarnings("JUnitTestCaseWithNoTests")
|
||||
public final class AdditionalTest extends SingleFileTranslationTest {
|
||||
|
||||
@NotNull
|
||||
private final String filename;
|
||||
|
||||
@SuppressWarnings("JUnitTestCaseWithNonTrivialConstructors")
|
||||
public AdditionalTest(@NotNull String filename) {
|
||||
super("additional/");
|
||||
this.filename = filename;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void runTest() throws Exception {
|
||||
runFunctionOutputTest(filename, Namer.getRootNamespaceName(), "box", "OK");
|
||||
}
|
||||
|
||||
public static Test suite() throws Exception {
|
||||
return TranslatorTestCaseBuilder
|
||||
.suiteForDirectory(BasicTest.pathToTestFilesRoot() + "additional/cases/", new TranslatorTestCaseBuilder.NamedTestFactory() {
|
||||
@NotNull
|
||||
@Override
|
||||
public Test createTest(@NotNull String filename) {
|
||||
AdditionalTest examplesTest = new AdditionalTest(filename);
|
||||
examplesTest.setName(filename);
|
||||
return examplesTest;
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
package org.jetbrains.k2js.test.semantics;
|
||||
|
||||
import org.jetbrains.k2js.test.SingleFileTranslationTest;
|
||||
|
||||
public class DefaultArgumentsTest extends SingleFileTranslationTest {
|
||||
|
||||
public DefaultArgumentsTest() {
|
||||
super("defaultArguments/");
|
||||
}
|
||||
|
||||
public void testConstructorCallWithDefArg1() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testConstructorCallWithDefArg2() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testDefArgsWithSuperCall() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testEnumWithDefArg() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testEnumWithOneDefArg() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testEnumWithTwoDefArgs() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testExtensionFunWithDefArgs() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testFunInAbstractClassWithDefArg() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testOverloadFunWithDefArg() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testOverrideValWithDefaultValue() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testVirtualCallWithDefArg() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
@@ -164,6 +164,8 @@ public final class Namer {
|
||||
private final JsName objectName;
|
||||
@NotNull
|
||||
private final JsName enumEntriesName;
|
||||
@NotNull
|
||||
private final JsExpression undefinedExpression;
|
||||
|
||||
@NotNull
|
||||
private final JsName isTypeName;
|
||||
@@ -181,6 +183,8 @@ public final class Namer {
|
||||
objectName = kotlinScope.declareName(OBJECT_OBJECT_NAME);
|
||||
|
||||
isTypeName = kotlinScope.declareName("isType");
|
||||
|
||||
undefinedExpression = new JsPrefixOperation(JsUnaryOperator.VOID, rootScope.getProgram().getNumberLiteral(0));
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@@ -278,4 +282,9 @@ public final class Namer {
|
||||
public JsInvocation enumEntriesObjectCreateInvocation() {
|
||||
return new JsInvocation(enumEntriesCreationMethodReference());
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public JsExpression getUndefinedExpression() {
|
||||
return undefinedExpression;
|
||||
}
|
||||
}
|
||||
|
||||
+12
-4
@@ -20,6 +20,7 @@ import com.google.dart.compiler.backend.js.ast.*;
|
||||
import com.intellij.util.SmartList;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.jetbrains.jet.lang.descriptors.CallableDescriptor;
|
||||
import org.jetbrains.jet.lang.descriptors.ConstructorDescriptor;
|
||||
import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor;
|
||||
import org.jetbrains.jet.lang.descriptors.PropertyDescriptor;
|
||||
@@ -27,11 +28,14 @@ import org.jetbrains.jet.lang.psi.JetClassOrObject;
|
||||
import org.jetbrains.jet.lang.psi.JetDelegationSpecifier;
|
||||
import org.jetbrains.jet.lang.psi.JetDelegatorToSuperCall;
|
||||
import org.jetbrains.jet.lang.psi.JetParameter;
|
||||
import org.jetbrains.jet.lang.resolve.BindingContext;
|
||||
import org.jetbrains.jet.lang.resolve.calls.model.ResolvedCall;
|
||||
import org.jetbrains.jet.lang.types.JetType;
|
||||
import org.jetbrains.jet.lexer.JetTokens;
|
||||
import org.jetbrains.k2js.translate.context.Namer;
|
||||
import org.jetbrains.k2js.translate.context.TranslationContext;
|
||||
import org.jetbrains.k2js.translate.general.AbstractTranslator;
|
||||
import org.jetbrains.k2js.translate.reference.CallArgumentTranslator;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
@@ -39,8 +43,8 @@ import java.util.List;
|
||||
|
||||
import static org.jetbrains.jet.lang.resolve.DescriptorUtils.getClassDescriptorForType;
|
||||
import static org.jetbrains.k2js.translate.utils.BindingUtils.*;
|
||||
import static org.jetbrains.k2js.translate.utils.FunctionBodyTranslator.setDefaultValueForArguments;
|
||||
import static org.jetbrains.k2js.translate.utils.PsiUtils.getPrimaryConstructorParameters;
|
||||
import static org.jetbrains.k2js.translate.utils.TranslationUtils.translateArgumentList;
|
||||
|
||||
public final class ClassInitializerTranslator extends AbstractTranslator {
|
||||
@NotNull
|
||||
@@ -66,12 +70,14 @@ public final class ClassInitializerTranslator extends AbstractTranslator {
|
||||
mayBeAddCallToSuperMethod(result);
|
||||
new InitializerVisitor(initializerStatements).traverseContainer(classDeclaration, context());
|
||||
|
||||
List<JsStatement> statements = result.getBody().getStatements();
|
||||
statements.addAll(setDefaultValueForArguments(primaryConstructor, context()));
|
||||
for (JsStatement statement : initializerStatements) {
|
||||
if (statement instanceof JsBlock) {
|
||||
result.getBody().getStatements().addAll(((JsBlock) statement).getStatements());
|
||||
statements.addAll(((JsBlock) statement).getStatements());
|
||||
}
|
||||
else {
|
||||
result.getBody().getStatements().add(statement);
|
||||
statements.add(statement);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -116,7 +122,9 @@ public final class ClassInitializerTranslator extends AbstractTranslator {
|
||||
|
||||
@NotNull
|
||||
private List<JsExpression> translateArguments(@NotNull JetDelegatorToSuperCall superCall) {
|
||||
return translateArgumentList(context(), superCall.getValueArguments());
|
||||
ResolvedCall<? extends CallableDescriptor> call = context().bindingContext().get(BindingContext.RESOLVED_CALL, superCall.getCalleeExpression());
|
||||
assert call != null : "ResolvedCall for superCall must be not null";
|
||||
return CallArgumentTranslator.translate(call, null, context()).getTranslateArguments();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
|
||||
+13
-6
@@ -34,8 +34,6 @@ import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
import static org.jetbrains.k2js.translate.utils.BindingUtils.getDefaultArgument;
|
||||
|
||||
public class CallArgumentTranslator extends AbstractTranslator {
|
||||
|
||||
@NotNull
|
||||
@@ -76,7 +74,6 @@ public class CallArgumentTranslator extends AbstractTranslator {
|
||||
|
||||
public static void translateSingleArgument(
|
||||
@NotNull ResolvedValueArgument actualArgument,
|
||||
@NotNull ValueParameterDescriptor parameterDescriptor,
|
||||
@NotNull List<JsExpression> result,
|
||||
@NotNull TranslationContext context,
|
||||
boolean shouldWrapVarargInArray
|
||||
@@ -86,8 +83,7 @@ public class CallArgumentTranslator extends AbstractTranslator {
|
||||
translateVarargArgument(valueArguments, result, context, shouldWrapVarargInArray);
|
||||
}
|
||||
else if (actualArgument instanceof DefaultValueArgument) {
|
||||
JetExpression defaultArgument = getDefaultArgument(context.bindingContext(), parameterDescriptor);
|
||||
result.add(Translation.translateAsExpression(defaultArgument, context));
|
||||
result.add(context.namer().getUndefinedExpression());
|
||||
}
|
||||
else {
|
||||
assert actualArgument instanceof ExpressionValueArgument;
|
||||
@@ -143,6 +139,15 @@ public class CallArgumentTranslator extends AbstractTranslator {
|
||||
this.isNativeFunctionCall = AnnotationsUtils.isNativeObject(resolvedCall.getCandidateDescriptor());
|
||||
}
|
||||
|
||||
private void removeLastUndefinedArguments(@NotNull List<JsExpression> result) {
|
||||
int i;
|
||||
for (i = result.size() - 1; i >= 0; i--) {
|
||||
if (result.get(i) != context().namer().getUndefinedExpression()) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
result.subList(i + 1, result.size()).clear();
|
||||
}
|
||||
|
||||
private ArgumentsInfo translate() {
|
||||
List<ValueParameterDescriptor> valueParameters = resolvedCall.getResultingDescriptor().getValueParameters();
|
||||
@@ -170,7 +175,7 @@ public class CallArgumentTranslator extends AbstractTranslator {
|
||||
}
|
||||
}
|
||||
|
||||
translateSingleArgument(actualArgument, parameterDescriptor, result, context(), !isNativeFunctionCall && !hasSpreadOperator);
|
||||
translateSingleArgument(actualArgument, result, context(), !isNativeFunctionCall && !hasSpreadOperator);
|
||||
}
|
||||
|
||||
if (isNativeFunctionCall && hasSpreadOperator) {
|
||||
@@ -187,6 +192,8 @@ public class CallArgumentTranslator extends AbstractTranslator {
|
||||
result.add(0, JsLiteral.NULL);
|
||||
}
|
||||
}
|
||||
|
||||
removeLastUndefinedArguments(result);
|
||||
return new ArgumentsInfo(result, hasSpreadOperator, cachedReceiver);
|
||||
}
|
||||
|
||||
|
||||
+3
-4
@@ -145,17 +145,16 @@ public final class InlinedCallExpressionTranslator extends AbstractCallExpressio
|
||||
@NotNull
|
||||
private TemporaryVariable createAliasForArgument(@NotNull ValueParameterDescriptor parameterDescriptor) {
|
||||
ResolvedValueArgument actualArgument = resolvedCall.getValueArgumentsByIndex().get(parameterDescriptor.getIndex());
|
||||
JsExpression translatedArgument = translateArgument(parameterDescriptor, actualArgument);
|
||||
JsExpression translatedArgument = translateArgument(actualArgument);
|
||||
TemporaryVariable aliasForArgument = context().declareTemporary(translatedArgument);
|
||||
context().addStatementToCurrentBlock(aliasForArgument.assignmentExpression().makeStmt());
|
||||
return aliasForArgument;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private JsExpression translateArgument(@NotNull ValueParameterDescriptor parameterDescriptor,
|
||||
@NotNull ResolvedValueArgument actualArgument) {
|
||||
private JsExpression translateArgument(@NotNull ResolvedValueArgument actualArgument) {
|
||||
List<JsExpression> result = new SmartList<JsExpression>();
|
||||
translateSingleArgument(actualArgument, parameterDescriptor, result, context(), true);
|
||||
translateSingleArgument(actualArgument, result, context(), true);
|
||||
assert result.size() == 1 : "We always wrap varargs in kotlin calls.";
|
||||
return result.get(0);
|
||||
}
|
||||
|
||||
+28
-5
@@ -16,12 +16,10 @@
|
||||
|
||||
package org.jetbrains.k2js.translate.utils;
|
||||
|
||||
import com.google.dart.compiler.backend.js.ast.JsBlock;
|
||||
import com.google.dart.compiler.backend.js.ast.JsExpression;
|
||||
import com.google.dart.compiler.backend.js.ast.JsNode;
|
||||
import com.google.dart.compiler.backend.js.ast.JsReturn;
|
||||
import com.google.dart.compiler.backend.js.ast.*;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.jet.lang.descriptors.FunctionDescriptor;
|
||||
import org.jetbrains.jet.lang.descriptors.ValueParameterDescriptor;
|
||||
import org.jetbrains.jet.lang.psi.JetDeclarationWithBody;
|
||||
import org.jetbrains.jet.lang.psi.JetExpression;
|
||||
import org.jetbrains.jet.lang.types.JetType;
|
||||
@@ -31,7 +29,13 @@ import org.jetbrains.k2js.translate.general.AbstractTranslator;
|
||||
import org.jetbrains.k2js.translate.general.Translation;
|
||||
import org.jetbrains.k2js.translate.utils.mutator.Mutator;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import static org.jetbrains.k2js.translate.utils.BindingUtils.getDefaultArgument;
|
||||
import static org.jetbrains.k2js.translate.utils.JsAstUtils.assignment;
|
||||
import static org.jetbrains.k2js.translate.utils.JsAstUtils.convertToBlock;
|
||||
import static org.jetbrains.k2js.translate.utils.JsAstUtils.equality;
|
||||
import static org.jetbrains.k2js.translate.utils.mutator.LastExpressionMutator.mutateLastExpression;
|
||||
|
||||
public final class FunctionBodyTranslator extends AbstractTranslator {
|
||||
@@ -43,6 +47,23 @@ public final class FunctionBodyTranslator extends AbstractTranslator {
|
||||
return (new FunctionBodyTranslator(descriptor, declarationWithBody, functionBodyContext)).translate();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static List<JsStatement> setDefaultValueForArguments(@NotNull FunctionDescriptor descriptor,
|
||||
@NotNull TranslationContext functionBodyContext) {
|
||||
List<JsStatement> result = new ArrayList<JsStatement>();
|
||||
for (ValueParameterDescriptor valueParameter : descriptor.getValueParameters()) {
|
||||
if (valueParameter.hasDefaultValue()) {
|
||||
JsNameRef jsNameRef = functionBodyContext.getNameForDescriptor(valueParameter).makeRef();
|
||||
JetExpression defaultArgument = getDefaultArgument(functionBodyContext.bindingContext(), valueParameter);
|
||||
JsExpression defaultValue = Translation.translateAsExpression(defaultArgument, functionBodyContext);
|
||||
|
||||
JsBinaryOperation checkArgIsUndefined = equality(jsNameRef, functionBodyContext.namer().getUndefinedExpression());
|
||||
JsIf jsIf = new JsIf(checkArgIsUndefined, assignment(jsNameRef, defaultValue).makeStmt());
|
||||
result.add(jsIf);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private final FunctionDescriptor descriptor;
|
||||
@@ -61,7 +82,9 @@ public final class FunctionBodyTranslator extends AbstractTranslator {
|
||||
private JsBlock translate() {
|
||||
JetExpression jetBodyExpression = declaration.getBodyExpression();
|
||||
assert jetBodyExpression != null : "Cannot translate a body of an abstract function.";
|
||||
return mayBeWrapWithReturn(Translation.translateExpression(jetBodyExpression, context()));
|
||||
JsBlock jsBlock = new JsBlock(setDefaultValueForArguments(descriptor, context()));
|
||||
jsBlock.getStatements().addAll(mayBeWrapWithReturn(Translation.translateExpression(jetBodyExpression, context())).getStatements());
|
||||
return jsBlock;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
|
||||
@@ -18,7 +18,6 @@ package org.jetbrains.k2js.translate.utils;
|
||||
|
||||
import com.google.dart.compiler.backend.js.ast.*;
|
||||
import com.intellij.openapi.util.Pair;
|
||||
import com.intellij.util.SmartList;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.jetbrains.jet.lang.descriptors.FunctionDescriptor;
|
||||
@@ -130,27 +129,6 @@ public final class TranslationUtils {
|
||||
return new JsConditional(testExpression, thenExpression, elseExpression);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static List<JsExpression> translateArgumentList(@NotNull TranslationContext context,
|
||||
@NotNull List<? extends ValueArgument> jetArguments) {
|
||||
if (jetArguments.isEmpty()) {
|
||||
return Collections.emptyList();
|
||||
}
|
||||
|
||||
List<JsExpression> jsArguments = new SmartList<JsExpression>();
|
||||
for (ValueArgument argument : jetArguments) {
|
||||
jsArguments.add(translateArgument(context, argument));
|
||||
}
|
||||
return jsArguments;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private static JsExpression translateArgument(@NotNull TranslationContext context, @NotNull ValueArgument argument) {
|
||||
JetExpression jetExpression = argument.getArgumentExpression();
|
||||
assert jetExpression != null : "Argument with no expression";
|
||||
return Translation.translateAsExpression(jetExpression, context);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static JsNameRef backingFieldReference(@NotNull TranslationContext context,
|
||||
@NotNull PropertyDescriptor descriptor) {
|
||||
|
||||
@@ -1,15 +0,0 @@
|
||||
|
||||
class C() {
|
||||
fun Any.toMyPrefixedString(prefix: String = "", suffix: String="") : String = prefix + " " + suffix
|
||||
|
||||
fun testReceiver() : String {
|
||||
val res : String = "mama".toMyPrefixedString("111", "222")
|
||||
return res
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
fun box() : String {
|
||||
if(C().testReceiver() != "111 222") return "fail"
|
||||
return "OK"
|
||||
}
|
||||
@@ -1,20 +0,0 @@
|
||||
trait A {
|
||||
fun bar2(arg: Int = 239) : Int
|
||||
|
||||
fun bar(arg: Int = 240) : Int = bar2(arg/2)
|
||||
}
|
||||
|
||||
open abstract class B() : A {
|
||||
override fun bar2(arg: Int) : Int = arg
|
||||
}
|
||||
|
||||
class C() : B() {
|
||||
}
|
||||
|
||||
fun box() : String {
|
||||
if(C().bar(10) != 5) return "fail"
|
||||
if(C().bar() != 120) return "fail"
|
||||
if(C().bar2() != 239) return "fail"
|
||||
if(C().bar2(10) != 10) return "fail"
|
||||
return "OK"
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
package foo
|
||||
|
||||
class A(val a: Int = 0)
|
||||
|
||||
class B(val a: Int = 0, val b: String = "a")
|
||||
|
||||
fun box(): String {
|
||||
val a0 = A()
|
||||
val a1 = A(1)
|
||||
if (a0.a != 0) return "a0.a != 0, it: ${a0.a}"
|
||||
if (a1.a != 1) return "a1.a != 1, it: ${a1.a}"
|
||||
|
||||
val b1 = B()
|
||||
if (b1.a != 0) return "b1.a != 0, it: ${b1.a}"
|
||||
if (b1.b != "a") return "b1.b != 'a', it: ${b1.b}"
|
||||
|
||||
val b2 = B(1)
|
||||
if (b2.a != 1) return "b2.a != 1, it: ${b2.a}"
|
||||
if (b2.b != "a") return "b2.b != 'a', it: ${b2.b}"
|
||||
|
||||
val b3 = B(b = "b")
|
||||
if (b3.a != 0) return "b3.a != 0, it: ${b3.a}"
|
||||
if (b3.b != "b") return "b3.b != 'b', it: ${b3.b}"
|
||||
|
||||
val b4 = B(2, "c")
|
||||
if (b4.a != 2) return "b4.a != 2, it: ${b4.a}"
|
||||
if (b4.b != "c") return "b4.b != 'c', it: ${b4.b}"
|
||||
|
||||
return "OK"
|
||||
}
|
||||
+2
@@ -1,3 +1,5 @@
|
||||
package foo
|
||||
|
||||
class T4(
|
||||
val c1: Boolean,
|
||||
val c2: Boolean,
|
||||
@@ -0,0 +1,12 @@
|
||||
package foo
|
||||
|
||||
open class A(val a: Int = 1, val b: Int = 2)
|
||||
|
||||
class B : A(b = 3)
|
||||
|
||||
fun box(): String {
|
||||
val b = B()
|
||||
if (b.a != 1) return "b.a != 1, it: ${b.a}"
|
||||
if (b.b != 3) return "b.a != 3, it: ${b.b}"
|
||||
return "OK"
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
package foo
|
||||
enum class A(val a: Int = 1) {
|
||||
FIRST: A()
|
||||
SECOND: A(2)
|
||||
}
|
||||
|
||||
fun box(): String {
|
||||
if (A.FIRST.a == 1 && A.SECOND.a == 2) {
|
||||
return "OK"
|
||||
}
|
||||
return "fail"
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
package foo
|
||||
enum class Foo(val a: Int = 1, val b: String) {
|
||||
B: Foo(2, "b")
|
||||
C: Foo(b = "b")
|
||||
}
|
||||
|
||||
fun box(): String {
|
||||
if (Foo.B.a != 2 || Foo.B.b != "b") return "fail1"
|
||||
if (Foo.C.a != 1 || Foo.C.b != "b") return "fail2"
|
||||
return "OK"
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
package foo
|
||||
enum class Foo(val a: Int = 1, val b: String = "a") {
|
||||
A: Foo()
|
||||
B: Foo(2, "b")
|
||||
C: Foo(b = "b")
|
||||
D: Foo(a = 2)
|
||||
}
|
||||
|
||||
fun box(): String {
|
||||
if (Foo.A.a != 1 || Foo.A.b != "a") return "fail1"
|
||||
if (Foo.B.a != 2 || Foo.B.b != "b") return "fail2"
|
||||
if (Foo.C.a != 1 || Foo.C.b != "b") return "fail3"
|
||||
if (Foo.D.a != 2 || Foo.D.b != "a") return "fail4"
|
||||
return "OK"
|
||||
}
|
||||
+2
@@ -1,3 +1,5 @@
|
||||
package foo
|
||||
|
||||
fun <T> T.toPrefixedString(prefix: String = "", suffix: String="") = prefix + toString() + suffix
|
||||
|
||||
fun box() : String {
|
||||
+4
-2
@@ -1,3 +1,5 @@
|
||||
package foo
|
||||
|
||||
open abstract class B() {
|
||||
fun foo(arg: Int = 239 + 1) : Int = arg
|
||||
}
|
||||
@@ -6,7 +8,7 @@ class C() : B() {
|
||||
}
|
||||
|
||||
fun box() : String {
|
||||
if(C().foo(10) != 10) return "fail"
|
||||
if(C().foo() != 240) return "fail"
|
||||
if(C().foo(10) != 10) return "fail1"
|
||||
if(C().foo() != 240) return "fail2"
|
||||
return "OK"
|
||||
}
|
||||
+4
-2
@@ -1,3 +1,5 @@
|
||||
package foo
|
||||
|
||||
open abstract class B() {
|
||||
abstract fun foo2(arg: Int = 239) : Int
|
||||
}
|
||||
@@ -7,7 +9,7 @@ class C() : B() {
|
||||
}
|
||||
|
||||
fun box() : String {
|
||||
if(C().foo2() != 239) return "fail"
|
||||
if(C().foo2(10) != 10) return "fail"
|
||||
if(C().foo2() != 239) return "fail1"
|
||||
if(C().foo2(10) != 10) return "fail2"
|
||||
return "OK"
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
package foo
|
||||
|
||||
open class A(open val bar: Int = 2) {
|
||||
val barA = bar
|
||||
}
|
||||
|
||||
class B(override val bar: Int = 3) : A()
|
||||
|
||||
|
||||
fun box() : String {
|
||||
val b = B()
|
||||
if (b.bar != 3) return "b.bar != 3, it: " + b.bar
|
||||
if (b.barA != 2) return "b.barA != 2, it: " + b.barA
|
||||
return "OK"
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
package foo
|
||||
|
||||
trait A {
|
||||
fun bar2(arg: Int = 239) : Int
|
||||
|
||||
fun bar(arg: Int = 240) : Int = bar2(arg/2)
|
||||
}
|
||||
|
||||
open abstract class B() : A {
|
||||
override fun bar2(arg: Int) : Int = arg
|
||||
}
|
||||
|
||||
class C() : B() {
|
||||
}
|
||||
|
||||
fun box() : String {
|
||||
if(C().bar(10) != 5) return "fail1: ${C().bar(10)}"
|
||||
if(C().bar() != 120) return "fail2: ${C().bar()}"
|
||||
if(C().bar2() != 239) return "fail3: ${C().bar2()}"
|
||||
if(C().bar2(10) != 10) return "fail4: ${C().bar2(10)}"
|
||||
return "OK"
|
||||
}
|
||||
Reference in New Issue
Block a user