1require 'test/unit' 2 3class Array 4 def iter_test1 5 collect{|e| [e, yield(e)]}.sort{|a,b|a[1]<=>b[1]} 6 end 7 def iter_test2 8 ary = collect{|e| [e, yield(e)]} 9 ary.sort{|a,b|a[1]<=>b[1]} 10 end 11end 12 13class TestIterator < Test::Unit::TestCase 14 def ttt 15 assert(iterator?) 16 end 17 18 def test_iterator 19 assert(!iterator?) 20 21 ttt{} 22 23 # yield at top level !! here's not toplevel 24 assert(!defined?(yield)) 25 end 26 27 def test_array 28 x = [1, 2, 3, 4] 29 y = [] 30 31 # iterator over array 32 for i in x 33 y.push i 34 end 35 assert_equal(x, y) 36 end 37 38 def tt 39 1.upto(10) {|i| 40 yield i 41 } 42 end 43 44 def tt2(dummy) 45 yield 1 46 end 47 48 def tt3(&block) 49 tt2(raise(ArgumentError,""),&block) 50 end 51 52 def test_nested_iterator 53 i = 0 54 tt{|j| break if j == 5} 55 assert_equal(0, i) 56 57 assert_raise(ArgumentError) do 58 tt3{} 59 end 60 end 61 62 def tt4 &block 63 tt2(raise(ArgumentError,""),&block) 64 end 65 66 def test_block_argument_without_paren 67 assert_raise(ArgumentError) do 68 tt4{} 69 end 70 end 71 72 # iterator break/redo/next 73 def test_break 74 done = true 75 loop{ 76 break 77 done = false # should not reach here 78 } 79 assert(done) 80 81 done = false 82 bad = false 83 loop { 84 break if done 85 done = true 86 next 87 bad = true # should not reach here 88 } 89 assert(!bad) 90 91 done = false 92 bad = false 93 loop { 94 break if done 95 done = true 96 redo 97 bad = true # should not reach here 98 } 99 assert(!bad) 100 101 x = [] 102 for i in 1 .. 7 103 x.push i 104 end 105 assert_equal(7, x.size) 106 assert_equal([1, 2, 3, 4, 5, 6, 7], x) 107 end 108 109 def test_append_method_to_built_in_class 110 x = [[1,2],[3,4],[5,6]] 111 assert_equal(x.iter_test1{|x|x}, x.iter_test2{|x|x}) 112 end 113 114 class IterTest 115 def initialize(e); @body = e; end 116 117 def each0(&block); @body.each(&block); end 118 def each1(&block); @body.each {|*x| block.call(*x) } end 119 def each2(&block); @body.each {|*x| block.call(x) } end 120 def each3(&block); @body.each {|x| block.call(*x) } end 121 def each4(&block); @body.each {|x| block.call(x) } end 122 def each5; @body.each {|*x| yield(*x) } end 123 def each6; @body.each {|*x| yield(x) } end 124 def each7; @body.each {|x| yield(*x) } end 125 def each8; @body.each {|x| yield(x) } end 126 127 def f(a) 128 a 129 end 130 end 131 132 def test_itertest 133 assert_equal([1], IterTest.new(nil).method(:f).to_proc.call([1])) 134 m = /\w+/.match("abc") 135 assert_equal([m], IterTest.new(nil).method(:f).to_proc.call([m])) 136 137 IterTest.new([0]).each0 {|x| assert_equal(0, x)} 138 IterTest.new([1]).each1 {|x| assert_equal(1, x)} 139 IterTest.new([2]).each2 {|x| assert_equal([2], x)} 140 IterTest.new([4]).each4 {|x| assert_equal(4, x)} 141 IterTest.new([5]).each5 {|x| assert_equal(5, x)} 142 IterTest.new([6]).each6 {|x| assert_equal([6], x)} 143 IterTest.new([8]).each8 {|x| assert_equal(8, x)} 144 145 IterTest.new([[0]]).each0 {|x| assert_equal([0], x)} 146 IterTest.new([[1]]).each1 {|x| assert_equal([1], x)} 147 IterTest.new([[2]]).each2 {|x| assert_equal([[2]], x)} 148 IterTest.new([[3]]).each3 {|x| assert_equal(3, x)} 149 IterTest.new([[4]]).each4 {|x| assert_equal([4], x)} 150 IterTest.new([[5]]).each5 {|x| assert_equal([5], x)} 151 IterTest.new([[6]]).each6 {|x| assert_equal([[6]], x)} 152 IterTest.new([[7]]).each7 {|x| assert_equal(7, x)} 153 IterTest.new([[8]]).each8 {|x| assert_equal([8], x)} 154 155 IterTest.new([[0,0]]).each0 {|*x| assert_equal([[0,0]], x)} 156 IterTest.new([[8,8]]).each8 {|*x| assert_equal([[8,8]], x)} 157 end 158 159 def m(var) 160 var 161 end 162 163 def m1 164 m(block_given?) 165 end 166 167 def m2 168 m(block_given?,&proc{}) 169 end 170 171 def test_block_given 172 assert(m1{p 'test'}) 173 assert(m2{p 'test'}) 174 assert(!m1()) 175 assert(!m2()) 176 end 177 178 def m3(var, &block) 179 m(yield(var), &block) 180 end 181 182 def m4(&block) 183 m(m1(), &block) 184 end 185 186 def test_block_passing 187 assert(!m4()) 188 assert(!m4 {}) 189 assert_equal(100, m3(10) {|x|x*x}) 190 end 191 192 class C 193 include Enumerable 194 def initialize 195 @a = [1,2,3] 196 end 197 def each(&block) 198 @a.each(&block) 199 end 200 end 201 202 def test_collect 203 assert_equal([1,2,3], C.new.collect{|n| n}) 204 end 205 206 def test_proc 207 assert_instance_of(Proc, lambda{}) 208 assert_instance_of(Proc, Proc.new{}) 209 lambda{|a|assert_equal(a, 1)}.call(1) 210 end 211 212 def test_block 213 assert_instance_of(NilClass, get_block) 214 assert_instance_of(Proc, get_block{}) 215 end 216 217 def test_argument 218 assert_nothing_raised {lambda{||}.call} 219 assert_raise(ArgumentError) {lambda{||}.call(1)} 220 assert_nothing_raised {lambda{|a,|}.call(1)} 221 assert_raise(ArgumentError) {lambda{|a,|}.call()} 222 assert_raise(ArgumentError) {lambda{|a,|}.call(1,2)} 223 end 224 225 def get_block(&block) 226 block 227 end 228 229 def test_get_block 230 assert_instance_of(Proc, get_block{}) 231 assert_nothing_raised {get_block{||}.call()} 232 assert_nothing_raised {get_block{||}.call(1)} 233 assert_nothing_raised {get_block{|a,|}.call(1)} 234 assert_nothing_raised {get_block{|a,|}.call()} 235 assert_nothing_raised {get_block{|a,|}.call(1,2)} 236 237 assert_nothing_raised {get_block(&lambda{||}).call()} 238 assert_raise(ArgumentError) {get_block(&lambda{||}).call(1)} 239 assert_nothing_raised {get_block(&lambda{|a,|}).call(1)} 240 assert_raise(ArgumentError) {get_block(&lambda{|a,|}).call(1,2)} 241 242 block = get_block{11} 243 assert_instance_of(Proc, block) 244 assert_instance_of(Proc, block.to_proc) 245 assert_equal(block.clone.call, 11) 246 assert_instance_of(Proc, get_block(&block)) 247 248 lmd = lambda{44} 249 assert_instance_of(Proc, lmd) 250 assert_instance_of(Proc, lmd.to_proc) 251 assert_equal(lmd.clone.call, 44) 252 assert_instance_of(Proc, get_block(&lmd)) 253 254 assert_equal(1, Proc.new{|a,| a}.call(1,2,3)) 255 assert_nothing_raised {Proc.new{|a,|}.call(1,2)} 256 end 257 258 def return1_test 259 Proc.new { 260 return 55 261 }.call + 5 262 end 263 264 def test_return1 265 assert_equal(55, return1_test()) 266 end 267 268 def return2_test 269 lambda { 270 return 55 271 }.call + 5 272 end 273 274 def test_return2 275 assert_equal(60, return2_test()) 276 end 277 278 def proc_call(&b) 279 b.call 280 end 281 def proc_yield() 282 yield 283 end 284 def proc_return1 285 proc_call{return 42}+1 286 end 287 288 def test_proc_return1 289 assert_equal(42, proc_return1()) 290 end 291 292 def proc_return2 293 proc_yield{return 42}+1 294 end 295 296 def test_proc_return2 297 assert_equal(42, proc_return2()) 298 end 299 300 def test_ljump 301 assert_raise(LocalJumpError) {get_block{break}.call} 302 303 # cannot use assert_nothing_raised due to passing block. 304 begin 305 val = lambda{break 11}.call 306 rescue LocalJumpError 307 assert(false, "LocalJumpError occurred from break in lambda") 308 else 309 assert_equal(11, val) 310 end 311 312 block = get_block{11} 313 lmd = lambda{44} 314 assert_equal(0, block.arity) 315 assert_equal(0, lmd.arity) 316 assert_equal(0, lambda{||}.arity) 317 assert_equal(1, lambda{|a|}.arity) 318 assert_equal(1, lambda{|a,|}.arity) 319 assert_equal(2, lambda{|a,b|}.arity) 320 end 321 322 def marity_test(m) 323 mobj = method(m) 324 assert_equal(mobj.arity, mobj.to_proc.arity) 325 end 326 327 def test_marity 328 marity_test(:assert) 329 marity_test(:marity_test) 330 marity_test(:p) 331 332 lambda(&method(:assert)).call(true) 333 lambda(&get_block{|a,n| assert(a,n)}).call(true, "marity") 334 end 335 336 def foo 337 yield(:key, :value) 338 end 339 def bar(&blk) 340 blk.call(:key, :value) 341 end 342 343 def test_yield_vs_call 344 foo{|k,v| assert_equal([:key, :value], [k,v])} 345 bar{|k,v| assert_equal([:key, :value], [k,v])} 346 end 347 348 class H 349 def each 350 yield [:key, :value] 351 end 352 alias each_pair each 353 end 354 355 def test_assoc_yield 356 [{:key=>:value}, H.new].each {|h| 357 h.each{|a| assert_equal([:key, :value], a)} 358 h.each{|a,| assert_equal(:key, a)} 359 h.each{|*a| assert_equal([[:key, :value]], a)} 360 h.each{|k,v| assert_equal([:key, :value], [k,v])} 361 h.each_pair{|a| assert_equal([:key, :value], a)} 362 h.each_pair{|a,| assert_equal(:key, a)} 363 h.each_pair{|*a| assert_equal([[:key, :value]], a)} 364 h.each_pair{|k,v| assert_equal([:key, :value], [k,v])} 365 } 366 end 367 368 class ITER_TEST1 369 def a 370 block_given? 371 end 372 end 373 374 class ITER_TEST2 < ITER_TEST1 375 include Test::Unit::Assertions 376 def a 377 assert(super) 378 super 379 end 380 end 381 382 def test_iter_test2 383 assert(ITER_TEST2.new.a {}) 384 end 385 386 class ITER_TEST3 387 def foo x 388 return yield if block_given? 389 x 390 end 391 end 392 393 class ITER_TEST4 < ITER_TEST3 394 include Test::Unit::Assertions 395 def foo x 396 assert_equal(super, yield) 397 assert_equal(x, super(x, &nil)) 398 end 399 end 400 401 def test_iter4 402 ITER_TEST4.new.foo(44){55} 403 end 404 405 def test_break__nested_loop1 406 _test_break__nested_loop1 do 407 break 408 end 409 end 410 411 def _test_break__nested_loop1 412 while true 413 yield 414 end 415 assert(false, "must not reach here") 416 end 417 418 def test_break__nested_loop2 419 _test_break__nested_loop2 do 420 break 421 end 422 end 423 424 def _test_break__nested_loop2 425 until false 426 yield 427 end 428 assert(false, "must not reach here") 429 end 430 431 def test_break__nested_loop3 432 _test_break__nested_loop3 do 433 break 434 end 435 end 436 437 def _test_break__nested_loop3 438 loop do 439 yield 440 end 441 assert(false, "must not reach here") 442 end 443 444 def test_break_from_enum 445 result = ["a"].inject("ng") {|x,y| break "ok"} 446 assert_equal("ok", result) 447 end 448 449 def _test_return_trace_func(x) 450 set_trace_func(proc {}) 451 [].fetch(2) {return x} 452 ensure 453 set_trace_func(nil) 454 end 455 456 def test_return_trace_func 457 ok = "returned gracefully" 458 result = "skipped" 459 result = _test_return_trace_func(ok) 460 ensure 461 assert_equal(ok, result) 462 return 463 end 464 465 class IterString < ::String 466 def ===(other) 467 super if !block_given? 468 end 469 end 470 471 # Check that the block passed to an iterator 472 # does not get propagated inappropriately 473 def test_block_given_within_iterator 474 assert_equal(["b"], ["a", "b", "c"].grep(IterString.new("b")) {|s| s}) 475 end 476 477 def test_enumerator 478 [1,2,3].each.with_index {|x,i| 479 assert_equal(x, i+1) 480 } 481 482 e = [1,2,3].each 483 assert_equal(1, e.next) 484 assert_equal(2, e.next) 485 assert_equal(3, e.next) 486 assert_raise(StopIteration){e.next} 487 e.rewind 488 assert_equal(1, e.next) 489 e.rewind 490 a = [] 491 loop{a.push e.next} 492 assert_equal([1,2,3], a) 493 494 assert_equal([[8, 1, 10], [6, 2, 11], [4, 3, 12]], 495 [8,6,4].zip((1..10),(10..100)).to_a) 496 end 497end 498