How to keep (print text) as it disappears when using compose ?
s: {hello test1 parse test2}
t1: "test1"
t2: "test2"
rule: compose [ thru (t1) mark: copy text to (t2) (print text)]
parse s rule
same question for compose/deep if it's different answer:
s: {hello test1 parse test2. hello second test for test1 parse test2.}
t1: "test1"
t2: "test2"
rule: compose/deep [ any [thru (t1) mark: copy text to (t2) (print text)]]
parse s rule
You aren't limited to what's in the box, so you could make your own COMPOSE-like construct that does other patterns.
For instance, here's a composeII which only substitutes for cases where there are nested parentheses. So it will leave (x) alone but evaluate ((x)).
composeII: function [block /only /deep] [
collect [
foreach item block [
case [
all [
paren? :item
1 = length? item
paren? first item
][
either only [
keep/only do first item
][
keep do first item
]
]
all [
deep
block? :item
][
either only [
keep/only composeII/deep/only item
][
keep/only composeII/deep item
]
]
true [
keep/only :item
]
]
]
]
]
So for your case:
>> t1: "test1"
>> t2: "test2"
>> composeII/deep [
any [thru ((t1)) mark: copy text to ((t2)) (print text)]
]
== [
any [thru "test1" mark: copy text to "test2" (print text)]
]
You can either convert block to paren, or quote paren:
>> compose [something here (to paren! [print text])]
== [something here (print text)]
>> compose [something here (quote (print text))]
== [something here (print text)]
It's the same for compose/deep .
As blocks shield their content from evaluation of compose you can also use
>> rule: compose [ thru (t1) mark: copy text to (t2) (first [(print text)] )]
== [thru "test1" mark: copy text to "test2" (print text)]
Related
I have the following problem. I need to loop through the code. However, it doesn't work.
Contextualizing the problem: I have 3 files (in .asc) that represent data referring to 3 ages of the turtles (age 2, age 4 and age 8). I would like if the user puts the value 1 in num-user, it would only do the simulation with only one file (L_2) that would represent [ "2" ] ; if the user puts the value 2 in num-user, he would do the simulation with the files (L_2 and L_4) that would represent [ "2" "4" ] and finally, if the user puts the value 3 in num-use, it would simulate the files (L_2 , L_4 and L_8) that would represent [ "2" "4" "8" ]. The problem is that the loop is not working and gives various errors. Like:
Extension exception: ascii file ./L_8.asc not found or Can't find element 3 of the list [2 4 8], which is only of length 3 or go runs more than 3 simulations.
I was unable to attach the .ascii files here in the question. But if anyone can look at the code and identify the error I would be very grateful. I can't use BehaviouSpace to solve the situation, I need this loop in the code.
Thanks in advance!
extensions [ gis ]
globals [ num turtle-ages num-ages files random-seeds num-user repetitions ]
to setup
ca
set random-seeds 1
random-seed random-seeds
set num 0
set turtle-ages [ "2" "4" "8" ]
set num-ages item num turtle-ages
setup-asc
setup-turtles
reset-ticks
end
to setup-2
clear
random-seed random-seeds
set num-ages item num turtle-ages
setup-asc
setup-turtles
reset-ticks
end
to setup-turtles
ask n-of 5 patches [ sprout 1 ]
end
to clear
set files 0
clear-ticks
clear-turtles
end
to setup-asc
let number1 num-ages
set files gis:load-dataset ( word "./L_" number1 ".asc" ) ;; this loads a one raster file. There are 3 files in the folder with the names: (L_2.asc ; L_4.asc and L_8.asc
end
to go
move
tick
let n count turtles
if n = 0 or ticks = 10
[
set random-seeds random-seeds + 1
set repetitions 1
if random-seeds = repetitions + 1
[
set random-seeds 1
set num num + 1
;; if the user puts the value 1 in num-user, it would only do the simulation with only one file (L_2) that would represent [ "2" ]
;;; if the user puts the value 2 in num-user, he would do the simulation with the files (L_2 and L_4) that would represent [ "2" "4" ]
;;;; and finally, if the user puts the value 3 in num-use, it would simulate the files (L_2 , L_4 and L_8) that would represent [ "2" "4" "8" ]
set num-user 1 ;;
if num = num-user [ stop ]
]
setup-2
]
end
to move
ask turtles [
right random 360
fd 1
if ticks = 5 [ die ]
]
end
Whenever possible, I'd suggest paring down your code to a MRE to a) make sure that users here can run your code (without your files, for example, this is not really viable) and b) to see if reframing your question / goals in simpler terms would help get things working- at least that's what works for me!
I think that you might find foreach useful here as a way to loop through your desired simulations instead of manually tracking the number of iterations. For this example, assuming num-user is a numeric input widget on the interface, the setup below will determine which of the ages to process:
globals [ ages-to-run ]
to base-setup
ca
; Determine how many simulations to run, based on user input into
; 'num-user' numerical input widget on the interface
ifelse num-user < 1 or num-user > 3 [
print "Incorrect number of simulations indicated"
] [
let possible-sims [ "2" "4" "8" ]
set ages-to-run sublist possible-sims 0 num-user
]
reset-ticks
end
After running the above, the ages-to-run variable will contain ["2"], ["2" "4"], or ["2" "4" "8"]. Next, you can iterate over those desired ages to run your simulations (a little more detail in comments):
to run-simulations
if ages-to-run = 0 [
print "Simulation setup not complete"
]
foreach ages-to-run [
; This is the loop proper where each "age" is iterated.
; All of your simulation calls (manual variable resetting,
; etc) should all go within this loop.
current-age ->
print word "Running simulations for age: " current-age
let file-to-load ( word "./L_" current-age ".asc" )
print file-to-load
clear-turtles
ask n-of 5 patches [
sprout 1 [
pd
set color runresult current-age + 55
]
]
repeat 20 [
ask turtles [
rt random 60 - 30
fd 1
]
tick
]
print ( word "Simulations complete for age: " current-age "\n" )
]
end
Running that code above with 3 entered into num-user will run a simulation for each age (different colors indicate different runs):
So to run simulations proper, all your per-age code should go within that foreach loop indicated above- and be careful, as you were in your question, to not reset global variables.
Situation: I have a code that exports turtle coordinates according to the code below:
to path
file-open (word fileName ".csv")
file-print (word self xcor " " ycor)
file-close
end
The result is something like:
(turtle 1)[1 1 1 1 1 2] [4 4 4 2 1 5]
Question: How can I export this same list, but with its items separated by commas?
From [1 2 1 1 1] to [1,2,1,1,1], for example.
Thanks in advance
If you are trying to process this in R or something after the fact, I'd recommend potentially reporting in long format (ie, each line indicates a turtle, a tick [or similar], and the coordinates)- I find it simpler to process.
To answer your actual question- one way would be to manually collapse each list of coordinates into a string separated by commas. For example, see the toy model below.
Simple setup:
extensions [csv]
globals [ test ]
turtles-own [ xcor-list ycor-list ]
to setup
ca
crt 10 [
set xcor-list []
set ycor-list []
]
repeat 5 [
ask turtles [
rt random 90 - 45
fd 1
set xcor-list lput pxcor xcor-list
set ycor-list lput pycor ycor-list
]
]
reset-ticks
end
This reporter is what's actually doing the work of collapsing the list into a simple string for output:
to-report collapse-string-list [str-list]
report reduce word ( sentence map [ str -> word str ", " ] but-last str-list last str-list )
end
And this chunk pulls the desired turtle variables into a list of lists, calls the collapse-string-list reporter on them, then exports to a csv:
to output-coord-file
let all-turtles sort turtles
; Pull coordinates from each turtle
let who-coord-list map [
current-turtle ->
(list
[who] of current-turtle
collapse-string-list [xcor-list] of current-turtle
collapse-string-list [ycor-list] of current-turtle
)] all-turtles
; Add headers
set who-coord-list fput ["who" "x" "y"] who-coord-list
; Export
csv:to-file "toy.csv" (map [ row -> (map [i -> (word i)] row ) ] who-coord-list)
end
Output:
I am trying to make a model in netlogo that can simulate various versions of langton's ant. I have the basic code already (which is not polished up yet, apologies for that). from a chooser in the interface, the user chooses a path that the ant (the turtle) takes, and turns either left or right depending on the color of the patch he is on. to turn the strings in the chooser into a usable code, I am using the following code (only partially included the walk execution, if you want the entire thig
to make-state-sequence
if mychoice = "[own input]"
[
ifelse 2 <= length own-LR-string and length own-LR-string <= 12 and remove "L" remove "R" own-LR-string = ""[
set state-sequence own-LR-string][print "Invalid, can only contain L and R, and must be 2-12 symbols" stop]
] set N length state-sequence
if mychoice = "[Random sequence]"
[
let random-length 2 + random 10
let random-sequence n-values random-length [one-of ["L" "R"]]
set state-sequence random-sequence
]
set N length state-sequence
if table:has-key? instruction-table mychoice [
set state-sequence table:get instruction-table mychoice]
set N length state-sequence
end
to walk
ask turtles [
if bumped? = true [stop]
let direction item [state] of patch-here state-sequence
if direction = "L" [
left 90
]
if direction = "R" [
right 90
]
here, the state-sequence is important; it is the string that is chosen in the chooser used in the interface.
doing this will make the setup button work fine, but using the walk button gives the following error:
ITEM expected input to be a string or list but got the number 0 instead.
I have tried turning the let direction item [state] of patch-here state-sequence portion into an ifelse statement; because if the symbol is not an L, it would automatically be an R. it didn't change the error.
I suspect the state-sequence is not recognised as a string. is there a possible fix for this? I also tried using a to-report in combination with reduce, but we got stuck on that as well.
for good measure, here are some snippets of the widgets in the interface:
the interface
the chooser editor
the info tab, if you would like to see it. has some deeper explanation on how langton's ant works.
As JenB commented above, it seems likely that "state-sequence" for "patch-here" was never initialized or set, so it has defaulted to the number 0.
You could check whether state-sequence was a list or string as the first real step in your ask turtles [ ] section and to throw an informative error if it is not.
Incidentally, your sequence of if-statements in make-state-sequence is a risky coding structure as zero or more than one of the conditions could fire. Possibly in your case zero of them were matched.
;; This structure may fire multiple conditions
;; with later actions possibly overriding earlier actions
;; and has the possibility that none of the conditions are met
;; If TWO conditions are matched, BOTH fire in that order and the SECOND one
;; may overwrite the FIRST one.
( condition1 ) [ action1 ]
( condition2 ) [ action2 ]
;; ...
( conditionn ) [ actionn ]
;; The following structure exits after the first succeessful condition is met.
;; and guarantees that there is always exactly one case matched
;; which might be the default case .
;; if a second condition might have been matched is unknown because the
;; code never gets that far.
;;
;; This is slightly obscurely hidden in the dictionary under "ifelse"
;; and further confused if you believe "choice" is a reserved word or the
;; only way you can test a condition. I tested the following and it works.
(
ifelse
( condition1 ) [ action1 ]
( condition2 ) [ action2 ]
;; ...
( conditionn ) [ actionn ]
;; else
[ default action ]
)
Here's sample code that demonstrates testing what value you have and showing that the zero value resulting from not having set the patches sequence could be detected by the
?is-string and ?is-list tests. It also demonstrates using the CHOICE structure.
patches-own [ x ]
to setup
clear-all
let z n-values 8 [one-of ["L" "R"]]
if is-list? z[ print "it's a list" ]
if is-string? z [ print "it's a string" ]
let a 46
let b 43
let c "dog"
let d "cat"
(
ifelse
( a = 4 ) [ print "a is 4 " ]
( b = 4 ) [ print "b is 4 " ]
( c = "dog" and d = "cat") [ print "strange choice "]
; else
[ print "I fell through to the else condition" ]
)
create-turtles 1
ask turtles [
print ( word "\n x = " x )
print ( word "is x a number? " is-number? x )
print ( word "is x a list? " is-list? x )
print ( word "is x a string? " is-string? x )
]
ask patch 0 0 [ set x n-values 8 [one-of ["L" "R"]]]
ask turtles [
print ( word "\n x = " x )
print ( word "is x a number? " is-number? x )
print ( word "is x a list? " is-list? x )
print ( word "is x a string? " is-string? x )
]
reset-ticks
end
In last example, probe value? 'a returns true as it detects 'a has value in global context. But I'd like to test 'a exclusively in local context, is there a syntax to do so ?
context [
probe value? 'a; false
]
context [
a: 1
probe value? 'a; true
]
; would like false instead of true
a: 1
context [
probe value? 'a; true
]
I think the simplest check would be
context [
probe in self 'a ; none
]
It returns none instead of false, but that is the only other falsy value anyway, so it's totally appropriate to check against. If you need it to be false, you can put to-logic in front.
Is it possible in Red to test value? for a variable inside a context not in global context?
By definition, no. Because there is no such thing as "the global context".
Remember that "Rebol (Red) actually does not have scope at all" ... "Rebol (Red) fakes it."
(See: Is there a overall explanation about definitional scoping in Rebol and Red)
Rebol has BIND? for asking an arbitrary ANY-WORD! where it's bound to (if anywhere). Red calls this CONTEXT?. So what you can do is ask if the binding of a word is to a context you care about.
ctx1: context [a: 10]
ctx2: context [a: 20]
word: bind 'a ctx1
print ctx1 = context? word ; true
print ctx2 = context? word ; false
So if what you mean by "global context" is actually the so-called SYSTEM/WORDS object, then that can be your test:
context [
probe value? 'a ; false
]
context [
a: 1
probe system/words <> context? 'a ; true
]
a: 1
context [
probe system/words <> context? 'a ; false
]
As to whether this is appropriate for your purposes, I don't know. Just remember there's no scope in Rebol/Red, unless you rig up some fake approximation that works well enough for what you're doing.
Here a solution without searching in the 'global' system/words, but in the 'local' self
>> a: 1
== 1
>> context [
[ probe all [
[ find words-of self 'a
[ value? pick find words-of self 'a 1
[ ]
[ probe value? 'a
[ ]
none
true
== make object! []
>>
>> context [
[ probe all [
[ find words-of self 'a
[ value? pick find words-of self 'a 1
[ ]
[ probe value? 'a
[ a: 2
[ ]
none
false
== make object! [
a: 2
]
>>
>> context [
[ a: 2
[ probe all [
[ find words-of self 'a
[ value? pick find words-of self 'a 1
[ ]
[ probe value? 'a
[ ]
true
true
== make object! [
a: 2
]
I don't manage to add a graphviz (#dot) to my doxygen documented VHDL files.
Can somebody provide some example code?
I would like to add fsm graphical representation to my code.
thanks in advance
Just write the dot-file manually:
digraph FSM {
RESET -> IDLE
IDLE -> CALC [label="data_in = '1'"]
CALC -> DONE
DONE -> IDLE
}
comment with --!;
start with #dot and stop with #enddot
Example:
--! #dot
--! digraph finite_state_machine {
--! rankdir=LR;
--! size="8,5"
--! node [shape = circle];
--! S0 -> S1 [ label = "010" ]
--! S1 -> S0 [ label = "000" ]
--! S1 -> S2 [ label = "111" ]
--! S2 -> S0 [ label = "101" ]
--! }
--! #enddot