git @ Cat's Eye Technologies noit-o-mnain-worb / rel_1_1_2000_0719
Initial import of noit o' mnain worb 1.1 revision 2000.0719. Cat's Eye Technologies 12 years ago
14 changed file(s) with 462 addition(s) and 0 deletion(s). Raw diff Collapse all Expand all
0 Copyright (c)2000, Cat's Eye Technologies.
1 All rights reserved.
2
3 Redistribution and use in source and binary forms, with or without
4 modification, are permitted provided that the following conditions
5 are met:
6
7 Redistributions of source code must retain the above copyright
8 notice, this list of conditions and the following disclaimer.
9
10 Redistributions in binary form must reproduce the above copyright
11 notice, this list of conditions and the following disclaimer in
12 the documentation and/or other materials provided with the
13 distribution.
14
15 Neither the name of Cat's Eye Technologies nor the names of its
16 contributors may be used to endorse or promote products derived
17 from this software without specific prior written permission.
18
19 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
20 CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
21 INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
22 MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
23 DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
24 LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
25 OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
26 PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
27 OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
28 ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
29 OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30 OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31 POSSIBILITY OF SUCH DAMAGE.
0 <html><head>
1 <meta http-equiv="Content-Type" content="text/html;CHARSET=iso-8859-1">
2 <meta name="Description" content="Cat's Eye Technologies: The "noit o' mnain worb" Language">
3 <title>Cat's Eye Technologies: The "noit o' mnain worb" Language</title>
4 <meta name="Keywords" content=" Cat's Eye Technologies Language
5 Programming computational computation non-deterministic
6 bobule concurrency constraint-based physics mechanics electronics
7 nondeterminstic fungeoid funge befunge experimental ">
8 </head>
9 <body>
10 <center>
11 <h1>noit o' mnain worb</h1>
12 </center><p><font size=-1>Version 1.1</font> <font size=-1>&nbsp;<img src="/images/icons/copyright.gif"
13 align=absmiddle width=12 height=12 alt="(c)" border=0>2000-2004 <a href="/">Cat's Eye Technologies</a>. All rights reserved.<br>
14 This software is OSI Certified Open Source Software.<br>
15 OSI Certified is a certification mark of the <a href="http://www.opensource.org/"><img src="/images/icons/webicon.gif" alt="[WWW]" border=0 width=12 height=12>Open Source Initiative</a>.<br>
16 See the file <a href="license.txt">license.txt</a> for license information.</font>
17 <hr>
18
19 <h3>What is <u>noit o' mnain worb</u>?</h3>
20
21 <p>The <u>noit o' mnain worb</u> language is a
22 non-deterministic particle automaton based on brownian motion (or entropy).
23
24 <p>A <u>noit o' mnain worb</u> runtime has an orthogonal gridwork
25 playfield (of any reasonable size or number of dimensions)
26 which is populated by any number of <i>bobules</i>. Bobules are <i>solid</i>
27 elements in this grid - that is, no two bobules may occupy the same location.
28 Bobules are also capable of motion - in fact they can hardly avoid it - and it is
29 important to note that they are stateless. As such, they have no idea which
30 direction they are going, nor what they are going to do when they get there.</p>
31
32 <p>Each time quantum, or <i>tick</i>, each bobule chooses an adjacent square
33 to move to, at random (in two dimensions, that's 8 possibilities
34 plus the possibility of not moving = 9 possibilities.)
35 If, during some tick, this randomly-chosen new location does not allow entry -
36 that is, if it is already occupied by a solid element (a bobule or a wall) - the
37 bobule does not move during that tick.</p>
38
39 <p>[Implementation note: each tick that a bobule is blocked from moving,
40 its "pressure" increases, although this is merely for visual effect.]</p>
41
42 <p>The playfield is made more interesting by the addition of:
43 <ul>
44 <li> <tt>#</tt> <i>walls</i> which are merely static solid elements that take up space and do not move;
45 <li> <tt>^v&gt;&lt;</tt> <i>diodes</i> which disallow bobules from passing through them backwards;
46 <li> <tt>+-</tt> <i>sources & sinks</i> which represent large repositories or vacancies of bobules; and
47 <li> <tt>!</tt> <i>loads</i> which represent something that the bobules can 'do'.
48 </ul></p>
49
50 <h3>Notes</h3>
51
52 <p>[Historical note: In version 1.0 (Jul 5 2000) of the language, which was released only
53 on the Cat's Eye Technologies Mailing List,
54 <tt>+-</tt> had much different (and much more myopic)
55 semantics than they do in v1.1.]</p>
56
57 <p>The sources and sinks are simply convenient 'macros', so that you can
58 build something like:</p>
59
60 <pre>
61 ###
62 ###+###
63 </pre>
64
65 <p>instead of saying something like:</p>
66
67 <pre>
68 #######
69 #.....#
70 #.....#
71 #.....#
72 ###.###
73 #.#
74 ###v###
75 </pre>
76
77 <p>Using the <tt>+</tt> sources and <tt>-</tt> sinks simply saves you
78 from specifying large chambers of bobules or emptiness explicitly.</p>
79
80 <p>[Implementation note: It is not the intention of the <tt>+</tt> element
81 to violate entropy, but the fact that, in the reference implementation, <tt>+</tt>
82 keeps producing bobules indefinately at a uniform rate of 10% chance per tick
83 does bend the rules a bit. In a more "entropically correct" implementation, the
84 chance per tick should decrease over time. Note that the language proper
85 does not specify any particular rate of bobule creation, but encourages
86 implementations to be flexible on this point.]</p>
87
88 <p>The <tt>!</tt> loads simply cause the implementation to react in some
89 noticable way when a bobule enters into their location, so that the
90 <u>noit o' mnain worb</u> programmer can pretend to themselves that their
91 bobules are 'doing something' during program runs.</p>
92
93 <p>[Implementation note: The reference interpreter simply outputs an ASCII
94 BEL character when this happens. On most terminals, this affects a beeping
95 sound.]</p>
96
97 <p>The idea is that the bobules, spaces, walls, and diodes alone constitute a (nearly)
98 Turing-Complete system.</p>
99
100 <p>I say "nearly" because it's actually missing a dimension in this form. The
101 <u>noit o' mnain worb</u> language isn't dimensionally-independent.
102 Notably, it doesn't work in one dimension at all.</p>
103
104 <p>It <i>almost</i> works in two dimensions, but the fact is that if you do not address
105 the 'wire-crossing problem' (see <a href="/projects/befunge93/">Befunge-93</a>'s
106 <tt>#</tt> instruction), you cannot
107 guarantee being able to connect two arbitrarily-chosen paths in two dimensions.
108 You need to have a way for coincident paths to cross, which is not strictly
109 just two dimensions anymore.</p>
110
111 <p>[Theoretical note: we suspect, but would surely have a hard time proving,
112 that this limitation is somehow related to the four-colour map theorem.]</p>
113
114 <p>So, it really only works in three dimensions and above. For that reason,
115 adding 'wormholes' to the <u>noit o' mnain worb</u> playfield is a possible
116 extension in the near future, to simulate three dimensions a la 'wire crossing'.</p>
117
118 </body></html>
0 ############
1 #..........#
2 #######v####
3 # #
4 #v####
5 # #
6 #v####
7 # #
8 #v####
9 # #
10 ######
0 #######
1 # < < #
2 # ### #
3 # >.> #
4 #######
0 ######################
1 # #
2 # #
3 # #
4 # #
5 # #
6 # + #
7 # #
8 # #
9 # #
10 # #
11 ######################
0 #########
1 #! ! ! !#
2 ###### ! ! ! ######
3 #+ ! ! ! ! -#
4 ###### ! ! ! ######
5 #! ! ! !#
6 #########
0 ######################
1 # #
2 # #
3 # #
4 # #
5 # - #
6 # + #
7 # #
8 # #
9 # #
10 # #
11 ######################
0 ##### #####
1 # ########### #
2 # . > < . #
3 # #####v##### #
4 ##### # ########
5 # >!#
6 #v#########
7 # #
8 ###
0 #######################
1 #..........> #
2 #######################
0 #####################
1 # < #
2 # ################# #
3 # # # #
4 # # #.#
5 # # # #
6 # ################# #
7 # > #
8 #####################
0 ###############
1 #.............#
2 #######v#######
3 # #
4 #########
5
0 ######################
1 #.......... #
2 #.......... #
3 #.......... #
4 #.......... #
5 #.......... #
6 #.......... #
7 #.......... #
8 #.......... #
9 #.......... #
10 #.......... #
11 ######################
0 ###
1 ### #+#
2 #+# # #
3 # ###v#
4 # < #
5 ### < #
6 # < #
7 ###v#
8 # #
9 #!#
10 #-#
11 ###
12
0 #/usr/local/bin/perl -w
1
2 # noit o' mnain worb - fungeoid language based on brownian motion
3 # v1.1 Jul 19 2000 Chris Pressey, Cat's Eye Technologies
4
5 # Copyright (c)2000, Cat's Eye Technologies.
6 # All rights reserved.
7 #
8 # Redistribution and use in source and binary forms, with or without
9 # modification, are permitted provided that the following conditions
10 # are met:
11 #
12 # Redistributions of source code must retain the above copyright
13 # notice, this list of conditions and the following disclaimer.
14 #
15 # Redistributions in binary form must reproduce the above copyright
16 # notice, this list of conditions and the following disclaimer in
17 # the documentation and/or other materials provided with the
18 # distribution.
19 #
20 # Neither the name of Cat's Eye Technologies nor the names of its
21 # contributors may be used to endorse or promote products derived
22 # from this software without specific prior written permission.
23 #
24 # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
25 # CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
26 # INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
27 # MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
28 # DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
29 # LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
30 # OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
31 # PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
32 # OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
33 # ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
34 # OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
35 # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
36 # POSSIBILITY OF SUCH DAMAGE.
37
38 # usage: [perl] worb[.pl] worb-playfield-file
39 # requirements: ANSI terminal emulation, for animation.
40
41 # history: v1.0 Jul 5 2000 - original release.
42 # v1.1 Jul 19 2000 - changed + and -
43 # optimized display routine for ANSI
44 # optimized is_bobule_at (cached)
45 # relicensed & released on web site
46
47 ### GLOBALS ###
48
49 @bobule = ();
50 @source = ();
51 @sink = ();
52 @playfield = ();
53
54 @bobule_at_cache = ();
55
56 $x = 0; $y = 0;
57
58 ### SUBS ###
59
60 sub draw_playfield
61 {
62 printf "%c[1;1H", 27; # gotoxy 1,1
63 my $i; my $j; my $p;
64 for($j = 0; $j <= $maxy; $j++)
65 {
66 for($i = 0; $i <= $maxx; $i++)
67 {
68 if ($p = is_bobule_at($i,$j))
69 {
70 if ($p == 1) { print '.'; }
71 elsif ($p >= 2 and $p <= 3) { print 'o'; }
72 elsif ($p >= 4 and $p <= 6) { print 'O'; }
73 elsif ($p >= 7 and $p <= 10) { print '0'; }
74 else { print '@'; }
75 } else
76 {
77 print $playfield[$i][$j];
78 }
79 }
80 print "\n";
81 }
82 }
83
84 sub is_bobule_at
85 {
86 my $x = shift; my $y = shift;
87 return $bobule_at_cache[$x][$y] || 0;
88 }
89
90 sub get_bobule_number_at
91 {
92 my $x = shift; my $y = shift;
93 my $i;
94 for ($i = 0; $i <= $#bobule; $i++)
95 {
96 return $i if $bobule[$i][0] == $x and $bobule[$i][1] == $y;
97 }
98 return undef;
99 }
100
101 sub vacant
102 {
103 my $x = shift; my $y = shift;
104 return 0 if $playfield[$x][$y] eq '#';
105 return 0 if is_bobule_at($x,$y);
106 return 1;
107 }
108
109 ### MAIN ###
110
111 open PLAYFIELD, $ARGV[0];
112 while(defined($line = <PLAYFIELD>))
113 {
114 my $i;
115 chomp($line);
116 for($i = 0; $i < length($line); $i++)
117 {
118 my $c = substr($line, $i, 1);
119 if ($c eq '.')
120 {
121 $c = ' ';
122 push @bobule, [$x, $y, 1];
123 $bobule_at_cache[$x][$y] = 1;
124 }
125 elsif ($c eq '+')
126 {
127 push @source, [$x, $y];
128 }
129 elsif ($c eq '-')
130 {
131 push @sink, [$x, $y];
132 }
133 $playfield[$x][$y] = $c;
134 $x++; if ($x > $maxx) { $maxx = $x; }
135 }
136 $x = 0;
137 $y++; if ($y > $maxy) { $maxy = $y; }
138 }
139 close PLAYFIELD;
140
141 printf "%c[2J", 27; # clear screen
142
143 draw_playfield();
144
145 $start_time = time();
146 $tick = 1;
147 while(1)
148 {
149 my $bobule; my $pole;
150 foreach $bobule (@bobule)
151 {
152 $bobule->[2]++;
153 if ($bobule->[2] == 2 or $bobule->[2] == 4 or $bobule->[2] == 7 or $bobule->[2] == 11)
154 {
155 my $p = $bobule->[2];
156 printf "%c[%d;%dH", 27, $bobule->[1]+1, $bobule->[0]+1;
157 if ($p == 2) { print 'o'; }
158 elsif ($p == 4) { print 'O'; }
159 elsif ($p == 7) { print '0'; }
160 elsif ($p == 11) { print '@'; }
161 }
162 $new_x = $bobule->[0] + int(rand(1) * 3)-1;
163 $new_y = $bobule->[1] + int(rand(1) * 3)-1;
164 next if not vacant($new_x, $new_y);
165 next if $playfield[$new_x][$new_y] eq '<' and $bobule->[0] < $new_x;
166 next if $playfield[$new_x][$new_y] eq '>' and $bobule->[0] > $new_x;
167 next if $playfield[$new_x][$new_y] eq '^' and $bobule->[1] < $new_y;
168 next if $playfield[$new_x][$new_y] eq 'v' and $bobule->[1] > $new_y;
169 next if $new_x == $bobule->[0] and $new_y == $bobule->[1];
170 print chr(7) if $playfield[$new_x][$new_y] eq '!';
171 printf "%c[%d;%dH%s", 27, $bobule->[1]+1, $bobule->[0]+1,
172 $playfield[$bobule->[0]][$bobule->[1]];
173 $bobule_at_cache[$bobule->[0]][$bobule->[1]] = 0;
174 $bobule->[0] = $new_x;
175 $bobule->[1] = $new_y;
176 $bobule_at_cache[$bobule->[0]][$bobule->[1]] = 1;
177 printf "%c[%d;%dH.", 27, $bobule->[1]+1, $bobule->[0]+1;
178 $bobule->[2] = 1;
179 }
180 foreach $pole (@source)
181 {
182 if (not is_bobule_at($pole->[0], $pole->[1]) and rand(1) < .1)
183 {
184 push @bobule, [$pole->[0], $pole->[1], 1];
185 $bobule_at_cache[$pole->[0]][$pole->[1]] = 1;
186 }
187 }
188 foreach $pole (@sink)
189 {
190 if (is_bobule_at($pole->[0], $pole->[1]) and rand(1) < .1)
191 {
192 my $q = get_bobule_number_at($pole->[0], $pole->[1]);
193 $bobule_at_cache[$pole->[0]][$pole->[1]] = 0;
194 $bobule[$q] = $bobule[$#bobule]; pop @bobule;
195 }
196 }
197 # track_time();
198 }
199
200 sub track_time
201 {
202 $tick++;
203 if ($tick > 1000)
204 {
205 $total_time = time() - $start_time;
206 $fps = int(1000 / $total_time);
207 die "Total time: $total_time seconds, approx fps: $fps\n";
208 }
209 }
210
211 ### END ###