Wiki

Ticket #326: named-params.patch

File named-params.patch, 33.9 KB (added by hopscc, 11 years ago)
  • Source/Members.cobra

     
    3232    get testMethods as IList<of TestMethod> 
    3333 
    3434    def matchesSignature(member as IBoxCodeMember) as bool 
    35      
     35    def getParamNamed(name as String) as Param? 
    3636 
    3737interface IOverloadable inherits IBoxCodeMember 
    3838    """ 
     
    345345        if (a inherits NilableType) <> (b inherits NilableType) 
    346346            return a.nonNil == b.nonNil 
    347347        return false 
     348         
     349    def getParamNamed(name as String) as Param? 
     350        for p in .params, if p.name == name, return p 
     351        return nil 
     352        # GenericParams in Methods??     
    348353 
    349  
    350354    ## Fields 
    351355 
    352356    def addMinFields is override 
  • Source/Expr.cobra

     
    313313            sb.append(', the call is supplying an arglist of type[Utils.plural(args)] "(') 
    314314            sep = '' 
    315315            for arg in args 
    316                 sb.append('[sep][arg.type.name]') 
     316                typeName = if(not arg.type , "(unknownType)", arg.type.name)                 
     317                sb.append('[sep][typeName]') 
    317318                sep=', ' 
    318319            sb.append(')".') 
    319320        return sb.toString 
    320          
     321     
    321322    def throwCannotFindMemberError(receiverExpr as Expr, memberName as String) 
    322323        __throwOrRecordCannotFindMemberError(receiverExpr, memberName, 1) 
    323324 
     
    333334            on 2, .recordError(errorMsg) 
    334335            else, throw FallThroughException(throwOrRecord) 
    335336 
     337    def recordCannotFindParamNamed(defn as IBoxCodeMember, name as String) 
     338        pNames = (for n in defn.params get n.name).join('", "') 
     339        detail = ' Names for this parameter list are "[pNames]".' 
     340        .recordError('There is no parameter named "[name]".[detail]')  
     341         
     342    def recordCannotFindParamNamedOrMember(expr as Expr, defn as IBoxCodeMember, name as String) 
     343        paramDetail='' 
     344        if defn.params.count 
     345            pNames = (for n in defn.params get n.name).join('", "') 
     346            paramDetail = 'Names for this parameter list are "[pNames]".' 
     347        memberSuggs = _suggestionsMessage(expr.suggestionsForBadMemberName(name)) 
     348        err = 'There is no parameter named "[name]" and no definition for "[name]" in "[expr.toCobraSource]"[expr.whoseTypeIsMessage].[paramDetail][memberSuggs]'  
     349        .recordError(err) 
     350                 
     351                 
    336352 
    337353interface IPotentialTypeExpr inherits IExpr 
    338354    """ 
     
    790806            # if .definition inherits BoxMember and .definition.isMethod and not dotNode.isImplicit 
    791807            if (.definition inherits AbstractMethod or .definition inherits MemberOverload) and not dotNode.isImplicit 
    792808                .compiler.warning(this, 'Unnecessary parentheses. You can remove them.') 
    793         else 
     809        else if not hasErrors 
    794810            for arg in _args 
    795                 if arg inherits AssignExpr 
    796                     .recordError('Cannot make assignments in arguments. This syntax is reserved in the future for keyword arguments.') 
    797  
     811                if arg inherits AssignExpr  # named arg in paramList 
     812                    hasKeywordArg = true 
     813                    if not arg.left inherits IdentifierExpr 
     814                        .recordError('General purpose assignments are not allowed as arguments. Assignment syntax can only be used for keyword arguments.') 
     815                    else 
     816                        paramName = (arg.left to IdentifierExpr).name 
     817                        defn = _definition to IBoxCodeMember 
     818                        param = defn.getParamNamed(paramName) 
     819                        if not param 
     820                            .recordCannotFindParamNamed(defn, paramName) 
     821                        arg.right.bindImp # 'x=y' has special treatment in arguments 
     822                else 
     823                    if hasKeywordArg 
     824                        .throwError('Cannot have a non-keyword argument ("[arg.toCobraSource]") after a keyword argument. All positional arguments must come before all keyword arguments.') 
     825                    #arg.bindImp 
     826             
    798827    ## _bindImp support 
    799828 
    800829    def _checkNoArgs(definition as BoxMember, args as IList<of Expr>) 
     
    19091938 
    19101939    var _expr as Expr 
    19111940    var _args as List<of Expr> 
    1912     var _hasKeywordArg as bool  # such as Foo(1, a=2) 
     1941    var _hasKeywordArg as bool  # such as Foo(1, a=2) # We could almost drop this 
    19131942    var _isForAttribute as bool  # see Attributes.cobra 
    19141943    var _helperMethod as Method? 
    19151944 
     
    19231952        base.addSubFields 
    19241953        .addField('expr', _expr) 
    19251954        .addField('args', _args) 
    1926         .addField('hasKeywordArg', .hasKeywordArg) 
    19271955        .addField('isForAttribute', .isForAttribute) 
    19281956 
    19291957    get allExprs as Expr* 
     
    19431971    get args from var 
    19441972        has Subnodes 
    19451973 
    1946     get hasKeywordArg from var 
    1947  
    19481974    pro isForAttribute from var 
    19491975 
    19501976    get name as String 
     
    19892015                return 
    19902016         
    19912017        expr = expr.bindImp 
    1992  
    19932018        if expr.definition inherits EnumDecl 
    19942019            enumCall = EnumCallExpr(.token, expr.toCobraSource, .args, expr.definition).bindImp 
    19952020            _type = enumCall.type to IType 
    19962021            _transformTo(enumCall) 
    19972022            return 
    19982023 
     2024        nPropertyInits = _verifyAndBindArgs(expr) 
     2025        _chkTypes(expr) 
     2026        _type ?= _hoistType(expr) # if _type not set in _chkTypes 
     2027 
     2028        #TODO:try and checkout initializer call 
     2029 
     2030        if _hasKeywordArg and nPropertyInits >0 and not .isForAttribute and not .hasError                
     2031            _makeHelperMethod 
     2032 
     2033    def _verifyAndBindArgs(expr as Expr) as int  
     2034        """ 
     2035        Check that the various argtypes are ordered correctly (positional, named and property-initialising) and  
     2036        where named refer to valid items (named params or properties). Bind the args for the argtypes 
     2037        """ 
     2038        gotInitCall = false 
     2039        nPropInits = nNamedParams =0 
     2040        badOrder= 'Incorrect arg ordering.' 
     2041        detail2 = 'all named parameter keyword arguments must be before all extendedInit (property initialising) keyword arguments' 
     2042        detail =  'All positional arguments must come before all keyword arguments, [detail2]' 
    19992043        for arg in .args 
    20002044            try 
    20012045                if arg inherits AssignExpr 
     
    20042048                        .recordError('General purpose assignments are not allowed as arguments. Assignment syntax can only be used for keyword arguments.') 
    20052049                    else if not expr.receiverType.isDynamicOrPassThrough 
    20062050                        propertyName = (arg.left to IdentifierExpr).name 
    2007                         if expr.memberForName(propertyName) is nil 
    2008                             .recordCannotFindMemberError(expr, propertyName) 
     2051                        if expr.memberForName(propertyName) #assign to property name post ctor (extended init) 
     2052                            nPropInits += 1 
     2053                        else 
     2054                            if not gotInitCall # lazy best Initializer determination 
     2055                                initCall = _bestInitializer 
     2056                                gotInitCall = true 
     2057                            defn = initCall to? IBoxCodeMember 
     2058                            if defn  
     2059                                if defn.getParamNamed(propertyName) #actually a named parameter  
     2060                                    nNamedParams += 1 
     2061                                    if nPropInits 
     2062                                        .recordError('[badOrder] Cannot have a named parameter argument ("[arg.toCobraSource]") after a keyword property initialising argument. [detail]') 
     2063                                else     
     2064                                    .recordCannotFindParamNamedOrMember(expr, defn, propertyName) 
     2065 
    20092066                    arg.right.bindImp  # 'x=y' has special treatment in arguments 
    20102067                else 
    20112068                    if _hasKeywordArg 
    2012                         .throwError('Cannot have a non-keyword argument ("[arg.toCobraSource]") after a keyword argument. All positional arguments must come before all keyword arguments.') 
     2069                        .throwError('[badOrder] Cannot have a positional non-keyword argument ("[arg.toCobraSource]") after a keyword argument. [detail]') 
    20132070                    arg.bindImp 
    20142071            catch ne as NodeException 
    20152072                .compiler.recordError(ne) 
    2016  
     2073        return nPropInits 
     2074             
     2075    def _bestInitializer as Initializer? 
     2076        # Since this is determining best Initializer choice from the provided args list we can still get  
     2077        # a bad result if the args include named params and the order is different from that in the decl. 
     2078        # OTOH using named params and default params should mean that there is only a single (well defaulted) 
     2079        # Initializer anyway... 
     2080        initCall = nil 
     2081        if _expr.definition inherits ClassOrStruct  # Class/Struct(o) MethodSig(?), Interface/Mixin(x) 
     2082            initdefn = _expr.memberForName('cue.init') 
     2083            if initdefn inherits BoxMember 
     2084                args = _argsToCallArgs 
     2085                if initdefn inherits MemberOverload 
     2086                    initCall = initdefn.computeBestOverload( args, nil, false) to Initializer? 
     2087                    #isOverload = true 
     2088                else if initdefn inherits Initializer 
     2089                    initCall = initdefn 
     2090                # TODO: verify args and params match exactly re count, assignability 
     2091                # maybe adjust inheritance tree to use code from CallExpr... 
     2092                /#  
     2093                params = initCall.params 
     2094                print params 
     2095                if initCall inherits BoxMember # .no-warnings. 
     2096                    if not initdefn.hasParams 
     2097                        _checkNoArgs(initCall, args) 
     2098                    else 
     2099                        params = initCall.params 
     2100                        if _checkParamsCount(initCall, args, params) 
     2101                            _checkArgsAssignable(initCall, isOverload, args, params) 
     2102                                 
     2103                _checkVisibility(definition, expr) 
     2104                #/ 
     2105            else 
     2106                throw FallThroughException(initdefn) 
     2107        return initCall          
     2108     
     2109    def _argsToCallArgs as List<of Expr> 
     2110        """get Positional and named args only - AssignExpr whose Identifier names are not property names.""" 
     2111        cleanArgs = List<of Expr>() 
     2112        for arg in .args 
     2113            if arg inherits AssignExpr  
     2114                if arg.left inherits IdentifierExpr 
     2115                    member = _expr.memberForName((arg.left to IdentifierExpr).name) 
     2116                if member, continue # extended init property assignment 
     2117            cleanArgs.add(arg) #positional arg or named (paramName=value) arg 
     2118        return cleanArgs 
     2119         
     2120    def _chkTypes(expr as Expr) 
     2121        """Make sure expr is one of supported grabbag of Types for a PostCallExpr or complain bitterly.""" 
    20172122        if expr inherits TypeExpr 
    20182123            # instantiation 
    20192124            assert expr.containedType 
     
    20372142            # which yielded: PostCallExpr(expr=ToExpr(...)) 
    20382143            # TODO: can probably make this an error now 
    20392144            assert false, _expr 
    2040  
    2041         if _type is nil 
    2042             assert expr.type is not nil 
    2043             exprType = expr.type.nonNil 
    2044             if exprType inherits MethodSig 
    2045                 _type = exprType.returnType 
    2046             else if exprType.isDescendantOf(.compiler.delegateType) 
    2047                 member = exprType.memberForName('invoke') 
    2048                 if member inherits Method 
    2049                     _type = member.resultType 
    2050                 else 
    2051                     .throwError('Cannot find a single "invoke" method for "_eventType.name".') 
    2052             else if expr.receiverType and expr.receiverType.nonNil.isSystemTypeClass 
    2053                 _type = .compiler.dynamicType 
    2054             else if exprType inherits Box 
    2055                 _type = expr.receiverType  # for example, an IdentifierExpr of 'SomeClass' has a .receiverType of that class 
    2056                 _handleClassInitializer 
    2057             else if exprType.isDynamic 
    2058                 _type = .compiler.nilableDynamicType 
    2059             else if expr.definition inherits NameSpace 
    2060                 .throwError('Cannot instantiate the namespace "[(expr.definition to NameSpace).fullName]".') 
    2061             else if exprType == .typeProvider.passThroughType 
    2062                 _type = .typeProvider.passThroughType 
     2145         
     2146    def _hoistType(expr as Expr) as IType? 
     2147        """Obtain supported-expression type for the postCallExpr's type.""" 
     2148        assert expr.type is not nil 
     2149        exprType = expr.type.nonNil 
     2150        if exprType inherits MethodSig 
     2151            type = exprType.returnType 
     2152        else if exprType.isDescendantOf(.compiler.delegateType) 
     2153            member = exprType.memberForName('invoke') 
     2154            if member inherits Method 
     2155                type = member.resultType 
    20632156            else 
    2064                 trace .idString, expr.idString, exprType.idString 
    2065                 trace this, expr 
    2066                 assert false, expr 
     2157                .throwError('Cannot find a single "invoke" method for "_eventType.name".') 
     2158        else if expr.receiverType and expr.receiverType.nonNil.isSystemTypeClass 
     2159            type = .compiler.dynamicType 
     2160        else if exprType inherits Box 
     2161            type = expr.receiverType  # for example, an IdentifierExpr of 'SomeClass' has a .receiverType of that class 
     2162            _handleClassInitializer 
     2163        else if exprType.isDynamic 
     2164            type = .compiler.nilableDynamicType 
     2165        else if expr.definition inherits NameSpace 
     2166            .throwError('Cannot instantiate the namespace "[(expr.definition to NameSpace).fullName]".') 
     2167        else if exprType == .typeProvider.passThroughType 
     2168            type = .typeProvider.passThroughType 
     2169        else 
     2170            trace .idString, expr.idString, exprType.idString 
     2171            trace this, expr 
     2172            assert false, expr 
    20672173 
    2068         if .hasKeywordArg and not .isForAttribute and not .hasError 
    2069             _makeHelperMethod 
     2174        return type 
    20702175             
    20712176    def _makeHelperMethod 
    20722177        """ 
    20732178        Add a private helper method to the current box to support extended initializer. 
    2074  
    2075         Foo(expr0, expr1, bar=expr2) --> 
     2179        Pass through any named parameter args. 
     2180         
     2181        Foo(expr0, expr1, paramName=expr2, bar=expr3) --> 
    20762182            call: 
    2077                 _ch_ext_init_1207(expr0, expr1, expr2) 
     2183                _ch_ext_init_1207(expr0, expr1, expr2, expr3) 
    20782184            def: 
    2079                 def _ch_ext_init_1207(arg0 as int, arg1 as int, /#bar=#/arg2 as int) 
    2080                     obj = Foo(arg0, arg1) 
    2081                     obj.bar = arg2 
     2185                def _ch_ext_init_1207(arg0 as int, arg1 as int, arg2 as int, /#bar=#/arg3 as int) 
     2186                    obj = Foo(arg0, arg1, paramName=arg2) 
     2187                    obj.bar = arg3 
    20822188                    return obj 
    20832189        """ 
    20842190        box, token = .compiler.curBox, box.token.copy 
    2085         paramsForDecl = List<of Param>() 
    2086         argsForInitCall = List<of Expr>()  # args to pass to `Foo(arg0, arg1)` 
    2087         propsToSet = List<of AssignExpr>()  # props to set as `obj.bar = arg2` etc. 
     2191        paramsForDecl = List<of Param>()   # parameters for helper method 
     2192        argsForInitCall = List<of Expr>()  # args to pass in call to `Foo(arg0, arg1)` 
     2193        propsToSet = List<of AssignExpr>() # Extended init props to set as `obj.bar = arg2` etc. 
    20882194        firstPropArg = -1 
    20892195        for i, arg in .args.numbered 
     2196            helperParamName = 'arg[i]' 
    20902197            if arg inherits AssignExpr 
    2091                 propsToSet.add(arg) 
    2092                 if firstPropArg == -1, firstPropArg = i 
    20932198                propertyName = (arg.left to IdentifierExpr).name 
    2094                 argType = _expr.memberForName(propertyName).resultType 
    2095                 arg = arg.right 
     2199                member = _expr.memberForName(propertyName) 
     2200                if member # ext Init property set 
     2201                    propsToSet.add(arg) 
     2202                    if firstPropArg == -1, firstPropArg = i 
     2203                    argType = member.resultType 
     2204                    #arg = arg.right 
     2205                else # named arg 
     2206                    helperParam = IdentifierExpr(token.copy('ID', helperParamName)) 
     2207                    helperNamedArg = AssignExpr(token.copy('ASSIGN', '='), 'ASSIGN', arg.left, helperParam) 
     2208                    argsForInitCall.add(helperNamedArg) 
     2209                    argType = arg.right.type to ! 
     2210                    #arg = arg.right 
    20962211            else 
    2097                 argsForInitCall.add(if(arg inherits NilLiteral, arg, IdentifierExpr(token.copy('ID', 'arg[i]')))) 
     2212                argsForInitCall.add(if(arg inherits NilLiteral, arg, IdentifierExpr(token.copy('ID', helperParamName)))) 
    20982213                argType = arg.type to ! 
    2099             paramsForDecl.add(Param(box.token.copy('ID', 'arg[i]'), argType)) 
     2214            paramsForDecl.add(Param(box.token.copy('ID', helperParamName), argType)) 
    21002215        name = '_ch_ext_init_[.serialNum]'  # ch = class helper, ext = extended, init = initializer 
    21012216        if .compiler.codeMemberStack.count 
    21022217            curMember = .compiler.curCodeMember 
  • Source/BackEndClr/SharpGenerator.cobra

     
    544544        d = writer.curlyToCobraLineNum 
    545545 
    546546        # Output 
     547        #print 'Output: ', writer.output 
    547548        (.compiler to Compiler).createSharpFile(.sharpFileName, writer.output) 
    548549 
    549550        return d 
     
    32803281        sep = '' 
    32813282        for arg in _args 
    32823283            sw.write(sep) 
    3283             arg.writeSharpDefInContext(sw) 
     3284            if arg inherits AssignExpr  #   .Net4.0 Named parameter 
     3285                # cant do arg.left.writeSharpDef as binding invariants are incomplete 
     3286                sw.write((arg.left to IdentifierExpr).name)  
     3287                sw.write(':')               # C# form is name:value 
     3288                arg.right.writeSharpDef(sw) 
     3289            else     
     3290                arg.writeSharpDefInContext(sw) 
    32843291            sep = ', ' 
    32853292        sw.write(')') 
    32863293 
     
    37073714    def writeSharpArgs(sw as CurlyWriter, sep as String) 
    37083715        for arg in _args 
    37093716            sw.write(sep) 
    3710             arg.writeSharpDefInContext(sw, false) 
     3717            if arg inherits AssignExpr  #   .Net4.0 Named parameter 
     3718                # cant do arg.left.writeSharpDef as binding invariants are incomplete 
     3719                sw.write((arg.left to IdentifierExpr).name)  
     3720                sw.write(':')               # C# form is name:value 
     3721                arg.right.writeSharpDef(sw) 
     3722            else     
     3723                arg.writeSharpDefInContext(sw, false) 
    37113724            sep = ',' 
    37123725         
    37133726    def writeSharpBreakdownItems(sw as CurlyWriter) 
  • Source/BackEndJvm/JavaGenerator.cobra

     
    13241324            on Direction.InOut, sw.write('/*inOut*/')   # default 
    13251325            on Direction.Out, sw.write('/*out*/')       # TODO 
    13261326        sw.write('[.type.javaParamRef] [.javaName]') 
    1327 #       if .optionalValue 
    1328 #           detail = 'For java at the moment you will need to recode the optional parameter method as a set of overloaded (possibly cascaded) methods with the desired number of parameters.' 
    1329 #           .compiler.warning(this, 'Java does not support optional parameters. Default parameter value setting is ignored. [detail]') 
     1327        if .optionalValue 
     1328            detail = 'For java at the moment you will need to recode the optional parameter method as a set of overloaded (possibly cascaded) methods with the desired number of parameters.' 
     1329            .compiler.warning(this, 'Java does not support optional parameters. Default parameter value setting is ignored. [detail]') 
     1330            # TODO: higher up write variant method that calls full param set method with default value curried in 
    13301331#           #sw.write('=') 
    13311332#           #_optValue.writeSharpDef(sw) 
    13321333 
     
    30343035        sep = '' 
    30353036        for arg in _args 
    30363037            sw.write(sep) 
    3037             arg.writeJavaDefInContext(sw) 
     3038            if arg inherits AssignExpr  #    Named parameter 
     3039                detail = 'For java at the moment you will need to recode the named parameter call to a call using positional arguments.' 
     3040                .compiler.warning(this, 'Java does not support named parameters in calls so these are not available with this backend. [detail]') 
     3041                # TODO: Rewrite call to positional parameter form using name(s) given 
     3042                ## cant do arg.left.writeSharpDef as binding invariants are incomplete 
     3043                #sw.write((arg.left to IdentifierExpr).name)  
     3044                #sw.write(':')              # C# form is name:value 
     3045                arg.right.writeJavaDef(sw) 
     3046            else     
     3047                arg.writeJavaDefInContext(sw) 
    30383048            sep = ', ' 
    30393049        sw.write(')') 
    30403050 
     
    46274637    def writeJavaArgs(sw as CurlyWriter, sep as String) 
    46284638        for arg in _args 
    46294639            sw.write(sep) 
    4630             arg.writeJavaDefInContext(sw, false) 
     4640            if arg inherits AssignExpr  #    Named parameter 
     4641                detail = 'For java at the moment you will need to recode the named parameter call to a call using positional arguments.' 
     4642                .compiler.warning(this, 'Java does not support named parameters in calls so these are are not available with this backend. [detail]') 
     4643                # TODO: Rewrite call to positional parameter form using name(s) given 
     4644                ## cant do arg.left.writeSharpDef as binding invariants are incomplete 
     4645                #sw.write((arg.left to IdentifierExpr).name)  
     4646                #sw.write(':')              # C# form is name:value 
     4647                arg.right.writeJavaDef(sw) 
     4648            else     
     4649                arg.writeJavaDefInContext(sw, false) 
    46314650            sep = ',' 
    46324651         
    46334652    def writeJavaBreakdownItems(sw as CurlyWriter) 
  • Tests/820-errors/200-expressions/150-no-assignments-in-args.cobra

     
    11class Test 
    22 
    33    def main is shared 
    4         Test().foo(x = 2)  # .error. Cannot make assignments in arguments. 
     4        Test().foo(x = 2)  # .error. no parameter named "x". 
    55 
    66    cue init 
    77        base.init 
  • Tests/120-classes/400-methods/600-named-params/820-name-mismatch.cobra

     
     1class NamedCtor 
     2    def main is shared 
     3 
     4        x1 = NamedCtor(sname='foo', age=99) #.error. No parameter named "sname" and no definition 
     5        assert x1.x == 'foo' 
     6        assert x1.a == 99 
     7         
     8    var x = '' 
     9    var a = 0 
     10     
     11    cue init(sName as String, age as int)    
     12        base.init 
     13        .x = sName 
     14        .a = age 
     15         
     16         
  • Tests/120-classes/400-methods/600-named-params/802-too-many-params.cobra

     
     1# fixed plus single named param + used optional + ext property init 
     2class OptParam 
     3    def main is shared 
     4         
     5        x = OptParam() 
     6        x.foo('default') 
     7        assert x.value == 0 
     8        assert x.value1 == 0 
     9 
     10        # can only set props like this in ctor calls 
     11        x.foo('opt', 45, value1=66 ) #.error. no parameter named "value1" 
     12        assert x.value ==45 
     13        assert x.value1 ==1 
     14 
     15    var value  = 0 
     16    var value1 = 0 
     17     
     18    def foo(s as String, nmd as int = 0, nmd1 as int = 0) 
     19        .value = nmd 
     20        if s =='default', assert nmd1 == 0 
     21        .value1 = nmd1 
     22         
  • Tests/120-classes/400-methods/600-named-params/826-order-mismatch.cobra

     
     1class NamedCtor 
     2    def main is shared 
     3 
     4        x1 = NamedCtor(sName='foo', age=99) 
     5        assert x1.x == 'foo' 
     6        assert x1.a == 99 
     7         
     8        x2 = NamedCtor(xcomb=88, sName='foo') #.error. Incorrect arg ordering 
     9        assert x2.x == 'wrong' # notReached 
     10        assert x2.a == 55 
     11        assert x2.xcomb == 88 
     12        assert x2.ycomb == 0 
     13         
     14        x2 = NamedCtor(xcomb=88, ycomb=99, sName='foo') #.error. Incorrect arg ordering 
     15        assert x2.x == 'wrong' # notReached 
     16        assert x2.a == 55 
     17        assert x2.xcomb == 88 
     18        assert x2.ycomb == 99 
     19         
     20        x3 = NamedCtor(xcomb=88, ycomb=99, 55) #.error. Incorrect arg ordering 
     21        assert x3.x == 'wrong' # notReached 
     22        assert x3.a == 55 
     23        assert x3.xcomb == 88 
     24        assert x3.ycomb == 99 
     25 
     26    var x = '' 
     27    var a = 0 
     28    pro xcomb from var = 0 
     29    pro ycomb from var = 0 
     30     
     31    cue init(sName as String = 'fou', age as int = 55)   
     32        base.init 
     33        .x = sName 
     34        .a = age 
     35         
     36         
  • Tests/120-classes/400-methods/600-named-params/804-too-many-params.cobra

     
     1# fixed plus single named param + used optional + ext property init 
     2class OptParam 
     3    def main is shared 
     4         
     5        x = OptParam() 
     6        x.foo('default', 44 ) 
     7        assert x.value == 44 
     8        assert x.value1 == 0 
     9 
     10        # valid named arg but already supplied by positional args 
     11        x.foo('opt', 45, 1, nmd1=66 ) #.error. expecting 3 arguments, but 4 are being supplied 
     12        assert x.value ==45 
     13        assert x.value1 ==66 
     14 
     15    var value  = 0 
     16    var value1 = 0 
     17     
     18    def foo(s as String, nmd as int, nmd1 as int = 0) 
     19        .value = nmd 
     20        if s =='default', assert nmd1 == 0 
     21        .value1 = nmd1 
     22         
  • Tests/120-classes/400-methods/600-named-params/810-no-param-named.cobra

     
     1# fixed plus single named param - errors 
     2class OptParam 
     3    def main is shared 
     4        x = OptParam() 
     5        x.call = 0 
     6        x.foo('default', badName = 44) # .error. no parameter 
     7        assert x.call ==44 
     8 
     9    var call = 0 
     10     
     11    def foo(s as String, nmd as int ) 
     12        #print s,i 
     13        .call = nmd 
     14 
  • Tests/120-classes/400-methods/600-named-params/110-named-params.cobra

     
     1# fixed plus single named param 
     2class OptParam 
     3    def main is shared 
     4        x = OptParam() 
     5        x.value = 0 
     6        x.foo('default', nmd=44) 
     7        assert x.value ==44 
     8             
     9        x.foo(nmd = 45, s='default') 
     10        assert x.value ==45 
     11 
     12    var value = 0 
     13     
     14    def foo(s as String, nmd as int ) 
     15        #print s,i 
     16        .value = nmd 
     17 
  • Tests/120-classes/400-methods/600-named-params/815-order-error.cobra

     
     1# fixed plus single named param + used optional 
     2class OptParam 
     3    def main is shared 
     4        x = OptParam() 
     5        x.value = 0 
     6        x.foo('default', nmd=44 ) 
     7        assert x.value ==44 
     8 
     9        x.foo('opt', nmd=50, 10 ) #.error. positional arguments must come before all keyword arguments 
     10        assert x.value ==50 
     11         
     12    var value = 0 
     13     
     14    def foo(s as String, nmd as int, nmd2 as int = 0) 
     15        #print s,i 
     16        trace nmd 
     17        .value = nmd 
     18        if s =='default', assert nmd2 == 0 
     19        trace nmd2 
     20        .value += nmd2 
     21 
  • Tests/120-classes/400-methods/600-named-params/850-badInit.cobra

     
     1# Change this later when add Initializer checks 
     2class BadI 
     3    def main is shared 
     4        x = BadI('default', 0, 10) #.error. not contain an initializer that takes 3 arguments 
     5        CobraCore.noOp(x) 
     6             
     7    var x = '' 
     8    var a = 0 
     9     
     10    cue init(sName as String, age as int)   # .warning. previous error 
     11        base.init 
     12        .x = sName 
     13        .a = age 
     14        #print 'NamedCtor [.x]' 
     15     
  • Tests/120-classes/400-methods/600-named-params/600-named-and-opt-and-ext.cobra

     
     1# fixed plus single named param + used optional + ext property init 
     2class OptParam 
     3    def main is shared 
     4         
     5        x = OptParam('default', nmd=45 ) 
     6        assert x.value ==45 
     7        assert x.value1 ==0 
     8        assert x.value2 ==0 
     9 
     10        x = OptParam('opt', 45, 1, value2=66 ) 
     11        assert x.value ==45 
     12        assert x.value1 ==1 
     13        assert x.value2 ==66 
     14         
     15        x = OptParam('opt', 0, nmd1=50, value2=67 ) 
     16        assert x.value ==0 
     17        assert x.value1 ==50 
     18        assert x.value2 ==67 
     19         
     20        x = OptParam('opt', nmd1=1, nmd=51, value2=68 ) 
     21        assert x.value ==51 
     22        assert x.value1 ==1 
     23        assert x.value2 ==68 
     24     
     25        x = OptParam('opt', nmd1=1, nmd=51, value1=55 ) 
     26        assert x.value ==51 
     27        assert x.value1 ==55 
     28        assert x.value2 ==0 
     29         
     30        x = OptParam('opt', nmd1=99, nmd=55, value=66, value1=77 ) 
     31        assert x.value  ==66 
     32        assert x.value1 ==77 
     33        assert x.value2 ==0 
     34         
     35        x = OptParam('opt', nmd1=99, nmd=55, value=66, value1=77, value2=88 ) 
     36        assert x.value  ==66 
     37        assert x.value1 ==77 
     38        assert x.value2 ==88 
     39         
     40    var value = 0 
     41    var value1 = 0 
     42    var value2 = 0 
     43     
     44    cue init(s as String, nmd as int, nmd1 as int = 0) 
     45        base.init 
     46        #trace nmd 
     47        .value = nmd 
     48        if s =='default', assert nmd1 == 0 
     49        #trace nmd1 
     50        .value1 = nmd1 
     51     
  • Tests/120-classes/400-methods/600-named-params/500-named-and-opt.cobra

     
     1# fixed plus single named param + unused optional param 
     2class OptParam 
     3    def main is shared 
     4        x = OptParam() 
     5        x.value = 0 
     6        x.foo('default', nmd=44 ) 
     7        assert x.value ==44 
     8         
     9        x.value = 0 
     10        x.foo('opt', nmd=10, nmd2=34) 
     11        assert x.value ==44 
     12 
     13        x.value = 0 
     14        x.foo('opt', nmd2=1, nmd=44) 
     15        assert x.value ==45 
     16     
     17         
     18    var value = 0 
     19     
     20    def foo(s as String, nmd as int, nmd2 as int = 0) 
     21        .value = nmd 
     22        .value += nmd2 
     23 
  • Tests/120-classes/400-methods/600-named-params/822-order-mismatch.cobra

     
     1class NamedCtor 
     2    def main is shared 
     3 
     4        x1 = NamedCtor(sName='foo', age=99) 
     5        assert x1.x == 'foo' 
     6        assert x1.a == 99 
     7         
     8        x2 = NamedCtor(age=55, xcomb=88, ycomb=99, sName='wrong') #.error. Incorrect arg ordering 
     9        assert x2.x == 'wrong' 
     10        assert x2.a == 55 
     11        assert x2.xcomb == 88 
     12        assert x2.ycomb == 99 
     13         
     14    var x = '' 
     15    var a = 0 
     16    pro xcomb from var = 0 
     17    pro ycomb from var = 0 
     18     
     19    cue init(sName as String, age as int)    
     20        base.init 
     21        .x = sName 
     22        .a = age 
     23         
     24         
  • Tests/120-classes/400-methods/600-named-params/510-named-and-opt.cobra

     
     1# fixed plus single named param + used optional 
     2class OptParam 
     3    def main is shared 
     4        x = OptParam() 
     5        x.clr 
     6        x.foo('default', 44 ) 
     7        assert x.value == 44 
     8        assert x.value1 == 0 
     9         
     10        x.clr 
     11        assert x.value ==0 and x.value1 ==0 
     12        x.foo('default', nmd=45 ) 
     13        assert x.value ==45 
     14        assert x.value1 ==0 
     15 
     16        x.clr 
     17        x.foo('opt', 45, 1 ) 
     18        assert x.value ==45 
     19        assert x.value1 ==1 
     20         
     21        x.clr 
     22        x.foo('opt', 0, nmd2=50 ) 
     23        assert x.value ==0 
     24        assert x.value1 ==50 
     25         
     26        x.clr 
     27        x.foo('opt', nmd2=1, nmd=51 ) 
     28        assert x.value ==51 
     29        assert x.value1 ==1 
     30     
     31        x.clr 
     32        x.foo('opt', nmd2=99, nmd=55 ) 
     33        assert x.value ==55 
     34        assert x.value1 ==99 
     35         
     36    var value = 0 
     37    var value1 = 0 
     38     
     39    def foo(s as String, nmd as int, nmd2 as int = 0) 
     40        #trace nmd 
     41        .value = nmd 
     42        if s =='default', assert nmd2 == 0 
     43        #trace nmd2 
     44        .value1 = nmd2 
     45     
     46    def clr 
     47        .value = .value1 = 0     
  • Tests/120-classes/400-methods/600-named-params/420-named-param-ext-ctor.cobra

     
     1class NamedCtor 
     2    def main is shared 
     3 
     4        x1 = NamedCtor(sName='foo', age=99) 
     5        assert x1.x == 'foo' 
     6        assert x1.a == 99 
     7         
     8        x2 = NamedCtor(age=55, sName='foo', ycomb=99) 
     9        assert x2.x == 'foo' 
     10        assert x2.a == 55 
     11        assert x2.ycomb == 99 
     12         
     13    var x = '' 
     14    var a = 0 
     15    pro ycomb from var = 0 
     16     
     17    cue init(sName as String, age as int)    
     18        base.init 
     19        .x = sName 
     20        .a = age 
     21        #print 'NamedCtor [.x]' 
     22         
     23         
  • Tests/120-classes/400-methods/600-named-params/824-order-mismatch.cobra

     
     1class NamedCtor 
     2    def main is shared 
     3 
     4        x1 = NamedCtor(sName='foo', age=99) 
     5        assert x1.x == 'foo' 
     6        assert x1.a == 99 
     7         
     8        x2 = NamedCtor("foo", xcomb=88, ycomb=99, 55) #.error. Incorrect arg ordering 
     9        assert x2.x == 'wrong' 
     10        assert x2.a == 55 
     11        assert x2.xcomb == 88 
     12        assert x2.ycomb == 99 
     13         
     14    var x = '' 
     15    var a = 0 
     16    pro xcomb from var = 0 
     17    pro ycomb from var = 0 
     18     
     19    cue init(sName as String, age as int)    
     20        base.init 
     21        .x = sName 
     22        .a = age 
     23         
     24         
  • Tests/120-classes/400-methods/600-named-params/410-named-param-ctor.cobra

     
     1class NamedCtor 
     2    def main is shared 
     3        x = NamedCtor('default', 0) 
     4        assert x.x == 'default' 
     5        assert x.a == 0 
     6 
     7        x1 = NamedCtor(sName='foo', age=99) 
     8        assert x1.x == 'foo' 
     9        assert x1.a == 99 
     10         
     11        x2 = NamedCtor(age=55, sName='foo') 
     12        assert x2.x == 'foo' 
     13        assert x2.a == 55 
     14         
     15    var x = '' 
     16    var a = 0 
     17     
     18    cue init(sName as String, age as int)    
     19        base.init 
     20        .x = sName 
     21        .a = age 
     22        #print 'NamedCtor [.x]' 
     23         
     24         
  • Tests/120-classes/400-methods/600-named-params/800-too-many-params.cobra

     
     1# fixed plus single named param + used optional + ext property init 
     2class OptParam 
     3    def main is shared 
     4         
     5        x = OptParam() 
     6        x.foo('default', 44 ) 
     7        assert x.value == 44 
     8        assert x.value1 == 0 
     9 
     10        # can only set props like this in ctor calls 
     11        x.foo('opt', 45, 1, value1=66 ) #.error. expecting 3 arguments, but 4 are being supplied 
     12        assert x.value ==45 
     13        assert x.value1 ==1 
     14 
     15    var value  = 0 
     16    var value1 = 0 
     17     
     18    def foo(s as String, nmd as int, nmd1 as int = 0) 
     19        .value = nmd 
     20        if s =='default', assert nmd1 == 0 
     21        .value1 = nmd1 
     22         
  • Tests/120-classes/322-construct-prop-set-error.cobra

     
    88 
    99    def main is shared 
    1010        x = X(t=5) 
    11         x = X(u=5)  # .error. cannot find 
     11        x = X(u=5)  # .error. no parameter named "u" and no definition for "u" 
    1212        print x