Loops/Nested: Difference between revisions
Line 288: | Line 288: | ||
The , after print element suppresses printing a line break. The above has been programmed on Python 2.6; I assume it also works on other Python 2.x versions, but it needs some minor changes in Python 3. |
The , after print element suppresses printing a line break. The above has been programmed on Python 2.6; I assume it also works on other Python 2.x versions, but it needs some minor changes in Python 3. |
||
But the normal way to solve this problem in Python is to use a return inside a function: |
|||
<lang python>from random import randint |
|||
def do_scan(m): |
|||
for row in m: |
|||
for item in row: |
|||
print item, |
|||
if item == 20: |
|||
print |
|||
return |
|||
print |
|||
m = [[randint(1, 20) for x in xrange(10)] for y in xrange(10)] |
|||
do_scan(m)</lang> |
|||
=={{header|Ruby}}== |
=={{header|Ruby}}== |
Revision as of 11:28, 23 June 2009
You are encouraged to solve this task according to the task description, using any language you may know.
Show a nested loop which searches two-dimensional array filled with random number uniformly distributed on [1..20]. The loops iterate rows and columns of the array printing the iterated elements of, until the value 20 is met.
Ada
<lang ada> with Ada.Text_IO; use Ada.Text_IO; with Ada.Numerics.Discrete_Random;
procedure Test_Loop_Nested is
type Value_Type is range 1..20; package Random_Values is new Ada.Numerics.Discrete_Random (Value_Type); use Random_Values; Dice : Generator; A : array (1..10, 1..10) of Value_Type := (others => (others => Random (Dice)));
begin
Outer :
for I in A'Range (1) loop for J in A'Range (2) loop Put (Value_Type'Image (A (I, J))); exit Outer when A (I, J) = 20; end loop; New_Line; end loop Outer;
end Test_Loop_Nested; </lang> Sample output:
16 3 1 17 13 5 4 2 19 1 5 5 17 15 17 2 5 5 17 13 16 10 10 20
AutoHotkey
<lang AutoHotkey>Loop, 10 {
i := A_Index Loop, 10 { j := A_Index Random, a%i%%j%, 1, 20 }
}
Loop, 10 {
i := A_Index Loop, 10 { j := A_Index If (a%i%%j% == 20) Goto finish }
}
finish:
MsgBox % "a[" . i . "][" . j . "]" is 20
Return</lang>
C
Using goto (note: gotos are considered harmful): <lang c>#include <stdlib.h>
- include <time.h>
- include <stdio.h>
int main() {
int a[10][10], i, j;
srand(time(NULL)); for (i = 0; i < 10; i++) for (j = 0; j < 10; j++) a[i][j] = rand() % 20 + 1;
for (i = 0; i < 10; i++) { for (j = 0; j < 10; j++) { printf(" %d", a[i][j]); if (a[i][j] == 20) goto Done; } printf("\n"); }
Done:
printf("\n"); return 0;
}</lang>
Common Lisp
<lang lisp>(let ((a (make-array '(10 10))))
(dotimes (i 10) (dotimes (j 10) (setf (aref a i j) (1+ (random 20))))) (block outer (dotimes (i 10) (dotimes (j 10) (princ " ") (princ (aref a i j)) (if (= 20 (aref a i j)) (return-from outer))) (terpri)) (terpri)))</lang>
D
<lang d>import std.stdio, std.random;
void main() {
int[10][10] m;
foreach (ref row; m) foreach (ref item; row) item = rand % 20 + 1;
outer: foreach (row; m) foreach (item; row) { writef(item, ' '); if (item == 20) break outer; }
writefln;
}</lang>
Forth
<lang forth> include random.fs
10 constant X 10 constant Y
- ,randoms ( range n -- ) 0 do dup random 1+ , loop drop ;
create 2darray 20 X Y * ,randoms
- main
Y 0 do cr X 0 do j X * i + cells 2darray + @ dup . 20 = if unloop unloop exit then loop loop ;
</lang>
Fortran
<lang fortran> program Example
implicit none
real :: ra(5,10) integer :: ia(5,10) integer :: i, j
call random_number(ra) ia = int(ra * 20.0) + 1
outer: do i = 1, size(ia, 1)
do j = 1, size(ia, 2) write(*, "(i3)", advance="no") ia(i,j) if (ia(i,j) == 20) exit outer end do write(*,*) end do outer
end program Example </lang> Sample output:
14 2 1 11 8 1 14 11 3 15 7 15 16 6 7 17 3 20
Java
<lang java>import java.util.Random;
public class NestedLoopTest {
public static final Random gen = new Random(); public static void main(String[] args) { int[][] a = new int[10][10]; for (int i = 0; i < a.length; i++) for (int j = 0; j < a[i].length; j++) a[i][j] = gen.nextInt(20) + 1;
Outer: for (int i = 0; i < a.length; i++) { for (int j = 0; j < a[i].length; j++) { System.out.print(" " + a[i][j]); if (a[i][j] == 20) break Outer; } System.out.println(); } System.out.println(); }
}</lang>
Logo
<lang logo> make "a mdarray [10 10]
for [j 1 10] [for [i 1 10] [mdsetitem list :i :j :a (1 + random 20)]]
to until.20
for [j 1 10] [ for [i 1 10] [ type mditem list :i :j :a type "| | if equal? 20 mditem list :i :j :a [stop] ] print "|| ]
end until.20 </lang>
Perl
<lang perl>my $a = [ map [ map { int(rand(20)) + 1 } 1 .. 10 ], 1 .. 10];
Outer: foreach (@$a) {
foreach (@$_) { print " $_"; if ($_ == 20) { last Outer; } } print "\n";
} print "\n";</lang>
PHP
<lang php><?php for ($i = 0; $i < 10; $i++)
for ($j = 0; $j < 10; $j++) $a[$i][$j] = rand(1, 20);
foreach ($a as $row) {
foreach ($row as $element) { echo " $element"; if ($element == 20) break 2; // 2 is the number of loops we want to break out of } echo "\n";
} echo "\n"; ?></lang>
Python
Python has only inner loop breaks. Below are two solutions around this problem, the first uses exception handling:
<lang python> import random class Found20(Exception):
pass
number_array = [[random.randrange(1,21) for x in xrange(10)] for y in xrange(10)]
try:
for row in number_array: for element in row: print element, if element == 20: raise Found20 print
except Found20:
</lang>
The second uses a flag variable:
<lang python> import random
number_array = [[random.randrange(1,21) for x in xrange(10)] for y in xrange(10)] found20 = False
for row in number_array:
for element in row: print element, if element == 20: found20 = True break print if found20: break
</lang>
The , after print element suppresses printing a line break. The above has been programmed on Python 2.6; I assume it also works on other Python 2.x versions, but it needs some minor changes in Python 3.
But the normal way to solve this problem in Python is to use a return inside a function: <lang python>from random import randint
def do_scan(m):
for row in m: for item in row: print item, if item == 20: print return print
m = [[randint(1, 20) for x in xrange(10)] for y in xrange(10)] do_scan(m)</lang>
Ruby
As the break command only jumps out of the innermost loop, this task requires Ruby's catch/throw
functionality.
<lang ruby>srand
ary = (1..20).to_a.shuffle.each_slice(4).to_a
p ary
catch :found_it do
for row in ary for element in row print "%2d " % element throw :found_it if element == 20 end puts "," end
end
puts "done"</lang>
[[2, 12, 10, 4], [18, 11, 9, 3], [14, 15, 7, 17], [6, 19, 8, 13], [1, 20, 16, 5]] 2 12 10 4 , 18 11 9 3 , 14 15 7 17 , 6 19 8 13 , 1 20 done
Tcl
Tcl only supports single-level breaks; exiting more deeply nested looping requires the use of exceptions, which are considerably more verbose before Tcl 8.6.
<lang tcl>set ary [subst [lrepeat 10 [lrepeat 5 {[expr int(rand()*20+1)]}]]]
try {
foreach row $ary { foreach col $row { puts -nonewline [format %3s $col] if {$col == 20} { throw MULTIBREAK "we're done" } } puts , }
} trap MULTIBREAK {} {} puts " done"</lang> Sample output:
12 13 14 13 15, 1 14 7 16 3, 12 11 5 1 9, 12 5 1 4 2, 6 11 11 4 11, 7 14 20 done