mirror of
https://github.com/nim-lang/Nim.git
synced 2026-04-22 07:15:22 +00:00
'var T' for iterators
This commit is contained in:
@@ -207,7 +207,7 @@ proc genAssignment(p: BProc, dest, src: TLoc, flags: TAssignmentFlags) =
|
||||
# This function replaces all other methods for generating
|
||||
# the assignment operation in C.
|
||||
if src.t != nil and src.t.kind == tyPtr:
|
||||
# little HACK to suppor the new 'var T' as return type:
|
||||
# little HACK to support the new 'var T' as return type:
|
||||
appcg(p, cpsStmts, "$1 = $2;$n", [rdLoc(dest), rdLoc(src)])
|
||||
return
|
||||
var ty = skipTypes(dest.t, abstractVarRange)
|
||||
|
||||
@@ -36,6 +36,15 @@ proc semExprWithType(c: PContext, n: PNode, flags: TExprFlags = {}): PNode =
|
||||
GlobalError(n.info, errExprXHasNoType,
|
||||
renderTree(result, {renderNoComments}))
|
||||
|
||||
proc semExprNoDeref(c: PContext, n: PNode, flags: TExprFlags = {}): PNode =
|
||||
result = semExpr(c, n, flags)
|
||||
if result.kind == nkEmpty:
|
||||
# do not produce another redundant error message:
|
||||
raiseRecoverableError()
|
||||
if result.typ == nil:
|
||||
GlobalError(n.info, errExprXHasNoType,
|
||||
renderTree(result, {renderNoComments}))
|
||||
|
||||
proc semSymGenericInstantiation(c: PContext, n: PNode, s: PSym): PNode =
|
||||
result = symChoice(c, n, s)
|
||||
|
||||
|
||||
@@ -167,6 +167,26 @@ proc SemReturn(c: PContext, n: PNode): PNode =
|
||||
if n[0][1].kind == nkSym and n[0][1].sym.kind == skResult:
|
||||
n.sons[0] = ast.emptyNode
|
||||
|
||||
proc SemYieldVarResult(c: PContext, n: PNode, restype: PType) =
|
||||
var t = skipTypes(restype, {tyGenericInst})
|
||||
case t.kind
|
||||
of tyVar:
|
||||
n.sons[0] = takeImplicitAddr(c, n.sons[0])
|
||||
of tyTuple:
|
||||
for i in 0.. <t.sonsLen:
|
||||
var e = skipTypes(t.sons[i], {tyGenericInst})
|
||||
if e.kind == tyVar:
|
||||
if n.sons[0].kind == nkPar:
|
||||
n.sons[0].sons[i] = takeImplicitAddr(c, n.sons[0].sons[i])
|
||||
elif n.sons[0].kind == nkHiddenSubConv and
|
||||
n.sons[0].sons[1].kind == nkPar:
|
||||
var a = n.sons[0].sons[1]
|
||||
a.sons[i] = takeImplicitAddr(c, a.sons[i])
|
||||
else:
|
||||
debug n.sons[0]
|
||||
localError(n.sons[0].info, errXExpected, "tuple constructor")
|
||||
else: nil
|
||||
|
||||
proc SemYield(c: PContext, n: PNode): PNode =
|
||||
result = n
|
||||
checkSonsLen(n, 1)
|
||||
@@ -178,7 +198,8 @@ proc SemYield(c: PContext, n: PNode): PNode =
|
||||
if restype != nil:
|
||||
n.sons[0] = fitNode(c, restype, n.sons[0])
|
||||
if n.sons[0].typ == nil: InternalError(n.info, "semYield")
|
||||
else:
|
||||
SemYieldVarResult(c, n, restype)
|
||||
else:
|
||||
localError(n.info, errCannotReturnExpr)
|
||||
|
||||
proc fitRemoveHiddenConv(c: PContext, typ: Ptype, n: PNode): PNode =
|
||||
@@ -361,7 +382,7 @@ proc semFor(c: PContext, n: PNode): PNode =
|
||||
checkMinSonsLen(n, 3)
|
||||
var length = sonsLen(n)
|
||||
openScope(c.tab)
|
||||
n.sons[length-2] = semExprWithType(c, n.sons[length-2], {efWantIterator})
|
||||
n.sons[length-2] = semExprNoDeref(c, n.sons[length-2], {efWantIterator})
|
||||
var call = n.sons[length-2]
|
||||
if call.kind != nkCall or call.sons[0].kind != nkSym or
|
||||
call.sons[0].sym.kind != skIterator:
|
||||
|
||||
@@ -502,9 +502,15 @@ proc transformFor(c: PTransf, n: PNode): PTransNode =
|
||||
addVar(v, newSymNode(temp))
|
||||
add(result, newAsgnStmt(c, newSymNode(temp), arg.ptransNode))
|
||||
IdNodeTablePut(newC.mapping, formal, newSymNode(temp))
|
||||
of paVarAsgn:
|
||||
of paVarAsgn:
|
||||
assert(skipTypes(formal.typ, abstractInst).kind == tyVar)
|
||||
InternalError(arg.info, "not implemented: pass to var parameter")
|
||||
# XXX why is this even necessary?
|
||||
var b = newNodeIT(nkHiddenAddr, arg.info, formal.typ)
|
||||
b.add(arg)
|
||||
arg = b
|
||||
IdNodeTablePut(newC.mapping, formal, arg)
|
||||
# XXX BUG still not correct if the arg has a side effect!
|
||||
#InternalError(arg.info, "not implemented: pass to var parameter")
|
||||
var body = newC.owner.ast.sons[codePos]
|
||||
pushInfoContext(n.info)
|
||||
inc(c.inlining)
|
||||
|
||||
5
examples/lazarus/backend.nim
Executable file
5
examples/lazarus/backend.nim
Executable file
@@ -0,0 +1,5 @@
|
||||
# Backend for the Lazarus GUI
|
||||
|
||||
proc myAdd*(x, y: int): int {.cdecl, exportc.} =
|
||||
result = x + y
|
||||
|
||||
29
tests/accept/run/tmoditer.nim
Normal file
29
tests/accept/run/tmoditer.nim
Normal file
@@ -0,0 +1,29 @@
|
||||
discard """
|
||||
output: "XXXXX01234"
|
||||
"""
|
||||
|
||||
iterator modPairs(a: var array[0..4,string]): tuple[key: int, val: var string] =
|
||||
for i in 0..a.high:
|
||||
yield (i, a[i])
|
||||
|
||||
iterator modItems*[T](a: var array[0..4,T]): var T =
|
||||
for i in 0..a.high:
|
||||
yield a[i]
|
||||
|
||||
var
|
||||
arr = ["a", "b", "c", "d", "e"]
|
||||
|
||||
for a in modItems(arr):
|
||||
a = "X"
|
||||
|
||||
for a in items(arr):
|
||||
stdout.write(a)
|
||||
|
||||
for i, a in modPairs(arr):
|
||||
a = $i
|
||||
|
||||
for a in items(arr):
|
||||
stdout.write(a)
|
||||
|
||||
echo ""
|
||||
|
||||
10
todo.txt
10
todo.txt
@@ -1,11 +1,10 @@
|
||||
Version 0.8.14
|
||||
==============
|
||||
|
||||
- fix serious bug that keeps teventemitter from compiling
|
||||
- ``var T`` as a return type:
|
||||
* for iterators
|
||||
* add ``modGet`` for generics
|
||||
* documentation
|
||||
* provide ``mod`` as an alternative syntax for ``var``
|
||||
- optional indentation for 'case' statement
|
||||
- make threadvar efficient again on linux after testing
|
||||
- test the sort implementation again
|
||||
@@ -19,8 +18,7 @@ version 0.9.0
|
||||
- add --deadlock_prevention:on|off switch? timeout for locks?
|
||||
- warning for implicit openArray -> varargs convention
|
||||
- implement explicit varargs
|
||||
- tests: run modules that contain "#RUN_ME", compile the other
|
||||
modules; run the GC tests
|
||||
- tests: run the GC tests
|
||||
- change overloading resolution
|
||||
- implement closures; implement proper coroutines
|
||||
|
||||
@@ -40,8 +38,6 @@ version 0.9.XX
|
||||
- implicit ref/ptr->var conversion; the compiler may store an object
|
||||
implicitly on the heap for write barrier efficiency; better:
|
||||
proc specialization in the code gen
|
||||
- resizing of strings/sequences could take into account the memory that
|
||||
is allocated
|
||||
- find a way to reintroduce the cleanup() pass for C code generation: this
|
||||
is hard because of partial evaluation --> symbol files will fix this as
|
||||
a side effect
|
||||
@@ -81,6 +77,8 @@ Low priority
|
||||
- find a way for easy constructors and destructors; (destructors are much more
|
||||
important than constructors)
|
||||
- code generated for type information is wasteful
|
||||
- resizing of strings/sequences could take into account the memory that
|
||||
is allocated
|
||||
|
||||
|
||||
Version 2
|
||||
|
||||
Reference in New Issue
Block a user