# Commands covered:  range, foreach, lindex, llength
#
# This file contains a collection of tests for one or more of the Tcl
# built-in commands.  Sourcing this file into Tcl runs the tests and
# generates output for errors.  No output means no errors were found.
#
# Copyright (c) 1991-1993 The Regents of the University of California.
# Copyright (c) 1994-1997 Sun Microsystems, Inc.
#
# See the file "license.terms" for information on usage and redistribution
# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
#
# RCS: @(#) $Id: foreach.test,v 1.9 2003/03/27 13:19:15 dkf Exp $

if {[lsearch [namespace children] ::tcltest] == -1} {
    package require tcltest
    namespace import -force ::tcltest::*
}

testConstraint testevalex [llength [info commands testevalex]]

# Basic "range" arithmetic sequences generated tests.

test range-1.1 {basic range tests} {
    range 0 10
} {0 1 2 3 4 5 6 7 8 9}

test range-1.2 {basic range tests} {
    range 10 0 -1
} {10 9 8 7 6 5 4 3 2 1}

test range-1.3 {basic range tests} {
    range 1 10 11
} {1}

test range-1.4 {basic range tests} {
    range 1 10 11
} {1}

test range-1.5 {basic range tests} {
    range 10 10
} {}

test range-1.6 {basic range tests} {
    range 10 10 2
} {}

test range-1.7 {basic range test} {
    range 5
} {0 1 2 3 4}

test range-1.8 {basic range test} {
    range -10 -20 -2
} {-10 -12 -14 -16 -18}

test range-1.9 {basic range test} {
    range -20 -10 3
} {-20 -17 -14 -11}

test range-2.0 {foreach range test} {
    set k 0
    foreach {x y} [range 100] {
	incr k [expr {$x*$y}]
    }
    set k
} {164150}

test range-2.1 {foreach range test without obj reuse} {
    set k 0
    set trash {}
    foreach {x y} [range 100] {
	incr k [expr {$x*$y}]
	lappend trash $x $y
    }
    set trash {}
    set k
} {164150}

test range-2.2 {range element shimmering test} {
    set k {}
    foreach x [range 0 10] {
	append k [llength $x]
    }
    set k
} {1111111111}

test range-3.0 {llength range test} {
    llength [range 5000]
} {5000}

test range-3.1 {llength range test} {
    llength [range 5000 5000]
} {0}

test range-4.0 {lindex range test} {
    lindex [range 1000] 500
} {500}

test range-4.1 {lindex range test} {
    lindex [range 1000] end-2
} {997}

test range-5.0 {lindex llength range test} {
    set k 0
    set trash {}
    set r [range 100]
    for {set i 0} {$i < [llength $r]} {incr i 2} {
	incr k [expr {[lindex $r $i]*[lindex $r [expr {$i+1}]]}]
    }
    set trash {}
    set k
} {164150}

test range-6.0 {not compiled foreach range test} testevalex {
    set k 0
    testevalex {
	foreach {x y} [range 100] {
	    incr k [expr {$x*$y}]
	}
    }
    set k
} {164150}

test range-7.0 {not compiled llength range test} testevalex {
    testevalex {llength [range 5000]}
} {5000}

test range-7.1 {not compiled llength range test} testevalex {
    testevalex {llength [range 5000 5000]}
} {0}

test range-8.0 {not compiled lindex range test} testevalex {
    testevalex {lindex [range 1000] 500}
} {500}

test range-8.1 {not compiled lindex range test} testevalex {
    testevalex {lindex [range 1000] end-2}
} {997}

test range-9.0 {not compiled lindex llength range test} testevalex {
    set k 0
    set trash {}
    set r [range 100]
    testevalex {
	for {set i 0} {$i < [llength $r]} {incr i 2} {
	    incr k [expr {[lindex $r $i]*[lindex $r [expr {$i+1}]]}]
	}
    }
    set trash {}
    set k
} {164150}

test range-10.0 {linked var range test} {
    catch {unset x}
    proc p0 var {
	upvar 1 $var v
	set k 0
	foreach v [range 0 200] {incr k $v}
	set k
    }
    set y [p0 x]
    list $x $y
} {199 19900}

catch {unset k}
catch {unset trash}
catch {unset i}
catch {unset x}
catch {unset y}
catch {unset r}

::tcltest::cleanupTests
