r3wp [groups: 83 posts: 189283]
  • Home
  • Script library
  • AltME Archive
  • Mailing list
  • Articles Index
  • Site search
 

World: r3wp

[I'm new] Ask any question, and a helpful person will try to answer.

mhinson
7-May-2009
[2156x2]
I added an extra string for the title and now get this similar failure

>> filenames: request-file/title/filter/path {Select all files to 
read} {x} [*.txt] %/D/Rebol/X/!conf/

** Script Error: Invalid argument: *.txt * *.r *.reb *.rip *.txt 
*.jpg *.gif *.bmp *.png
** Where: request-file
** Near: done: local-request-file data: reduce

[tt/text ob/text clean-path where picked filt-names filt-values found? 
any [only]...
AH a string "*.txt" for the filter works   Thanks for your help
Gregg
11-May-2009
[2158x2]
Large message coming, with examples of showing progress. Note that 
it uses INCLUDE and FILE-LIST, so adapt accordingly, and let me know 
if I left any other dependencies in it that cause it not to work. 
It was quickly hacked from existing code.
REBOL []

do %include.r
include %file-list.r


flash-wnd: flash "Finding test files..."

if file: request-file/only [
    files: read first split-path file
]
if none? file [halt]

items: collect/only item [
    foreach file files [item: reduce [file none]]
]

unview/only flash-wnd



;-------------------------------------------------------------------------------
;-- Generic functions

call*: func [cmd] [
    either find first :call /show [call/show cmd] [call cmd]
]

change-each: func [
    [throw]

    "Change each value in the series by applying a function to it"

    'word   [word!] "Word or block of words to set each time (will be 
    local)"
    series  [series!] "The series to traverse"

    body    [block!] "Block to evaluate. Return value to change current 
    item to."
    /local do-body
][
    do-body: func reduce [[throw] word] body
    forall series [change/only series do-body series/1]

    ; The newer FORALL doesn't return the series at the tail like the 
    old one

    ; did, but it will return the result of the block, which is CHANGE's 
    result,
    ; so we need to explicitly return the series here.
    series
]

collect: func [
    "Collects block evaluations." [throw]
    'word
    block [block!] "Block to evaluate."
    /into dest [block!] "Where to append results"
    /only "Insert series results as series"

    /local fn code marker at-marker? marker* mark replace-marker rules
][
    block: copy/deep block
    dest: any [dest make block! []]

    fn: func [val] compose [(pick [insert insert/only] not only) tail 
    dest get/any 'val

        get/any 'val
    ]
    code: 'fn
    marker: to set-word! word
    at-marker?: does [mark/1 = marker]
    replace-marker: does [change/part mark code 1]
    marker*: [mark: set-word! (if at-marker? [replace-marker])]
    parse block rules: [any [marker* | into rules | skip]]
    do block
    head :dest
]

edit-file: func [file] [
    ;print mold file

    call* join "notepad.exe " to-local-file file ;join test-file-dir 
    file
]

flatten: func [block [any-block!]][
    parse block [

        any [block: any-block! (change/part block first block 1) :block | 
        skip]
    ]
    head block
]

logic-to-words: func [block] [

    change-each val block [either logic? val [to word! form val] [:val]]
]

standardize: func [

    "Make sure a block contains standard key-value pairs, using a template 
    block"
    block    [block!] "Block to standardize"
    template [block!] "Key value template pairs"
][
    foreach [key val] template [
        if not found? find/skip block key 2 [
            repend block [key val]
        ]
    ]
]

tally: func [

    "Counts values in the series; returns a block of [value count] sub-blocks."
    series [series!]
    /local result blk
][
    result: make block! length? unique series

    foreach value unique series [repend result [value reduce [value 0]]]
    foreach value series [
        blk: first next find/skip result value 2
        blk/2: blk/2 + 1
    ]
    extract next result 2
]


;-------------------------------------------------------------------------------

counts: none

refresh: has [i] [
    reset-counts
    i: 0
    foreach item items [
        i: i + 1
        set-status reform ["Testing" mold item/1]
        item/2: random/only reduce [true false]
        show main-lst
        set-face f-prog i / length? items
        wait .25
    ]
    update-counts
    set-status mold counts
]

reset-counts: does [counts: copy [total 0 passed 0 failed 0]]

set-status: func [value] [set-face status form value]

update-counts: has [pass-fail] [
    counts/total: length? items

    pass-fail: logic-to-words flatten tally collect res [foreach item 
    items [res: item/2]]
    ;result (e.g.): [true 2012 false 232]
    standardize pass-fail [true 0 false 0]
    counts/passed: pass-fail/true
    counts/failed: pass-fail/false
]

;---------------------------------------------------------------


main-lst: sld: ; The list and slider faces
c-1:           ; A face we use for some sizing calculations
    none
ml-cnt:        ; Used to track the result list slider value.
visible-rows:  ; How many result items are visible at one time.
    0

lay: layout [
    origin 5x5
    space 1x0
    across

    style col-hdr text 100 center black mint - 20

    text 600 navy bold {

        This is a sample using file-list and updating progress as files are
        processed. 
    }
    return
    pad 0x10

    col-hdr "Result"  col-hdr 400 "File" col-hdr 100
    return
    pad -2x0

    ; The first block for a LIST specifies the sub-layout of a "row",

    ; which can be any valid layout, not just a simple "line" of data.

    ; The SUPPLY block for a list is the code that gets called to display

    ; data, in this case as the list is scrolled. Here COUNT tells us

    ; which ~visible~ row data is being requested for. We add that to 
    the

    ; offset (ML-CNT) set as the slider is moved. INDEX tells us which
    ; ~face~ in the sub-layout the data is going to.

    ; COUNT is defined in the list style itself, as a local variable 
    in
    ; the 'pane function.
    main-lst: list 607x300 [
        across space 1x0 origin 0x0
        style cell text 100x20 black mint + 25 center middle
        c-1: cell  cell 400 left   cell [edit-file item/1]
    ] supply [
        count: count + ml-cnt
        item: pick items count
        face/text: either item [
            switch index [
                1 [

                    face/color: switch item/2 reduce [none [gray] false [red] true [green]]
                    item/2
                ]
                2 [mold item/1]
                3 ["Edit"]
            ]
        ] [none]
    ]

    sld: scroller 16x298 [ ; use SLIDER for older versions of View

        if ml-cnt <> (val: to-integer value * subtract length? items visible-rows) 
        [
            ml-cnt: val
            show main-lst
        ]
    ]
    return
    pad 0x20
    f-prog: progress 600x16
    return
    status: text 500 return
    button 200 "Run" [refresh  show lay]
    pad 200
    button "Quit" #"^q" [quit]
]

visible-rows: to integer! (main-lst/size/y / c-1/size/y)

either visible-rows >= length? items [
    sld/step: 0
    sld/redrag 1
][
    sld/step: 1 / ((length? items) - visible-rows)
    sld/redrag (max 1 visible-rows) / length? items
]

view lay
mhinson
12-May-2009
[2160]
Hi, I am trying to reduce the number of global variables I use in 
functions & so my functions return blocks, but I have not discovered 
any simple way to dereference the information in the variables, within 
the blocks..  I have written a function to do it, but I guess there 
is a built in function if I could find it. Or at least something 
a bit more elegant than this: "return_value_of_block_component" function. 
  Any tips most welcome please.

f1: func [a] [
	b: join a "-Bee"
	c: join a "-Cee"
	return [b c]
]

d: f1 {Hi}

return_value_of_block_component: func [block component] [
	foreach element block [
	if element = component [return reduce [element]]
	]
]

H: return_value_of_block_component d 'b
I: return_value_of_block_component d 'c

print H
print I
BrianH
12-May-2009
[2161]
For f1, reduce the block before you return it. Then use set [a b] 
f1 "blah" to get the values.
Henrik
12-May-2009
[2162]
about returning complex values: generally it's easier to just pass 
objects around.
mhinson
12-May-2009
[2163]
Brian if I reduce the block I cant reference the values in the block 
by name (b & c in my example). or perhaps I dont know how to?
BrianH
12-May-2009
[2164]
If you need the names, create an object and return that like Henrik 
says. If you need the values, my method will work.
Henrik
12-May-2009
[2165]
vars: make object! [
	b: c: none
]

f1: func [a] [
	vars/b: join a "-Bee"
	vars/c: join b "-Cee"
	vars
]
mhinson
12-May-2009
[2166]
I see, it looks as if both techniques will help me in different cases
Henrik
12-May-2009
[2167]
when using objects, you will have less maintenance and you have one 
place where your object contents is defined. imagine if you have 
10 different functions that would return blocks (10 block definitions) 
versus 10 functions that return objects (1 object definition).
mhinson
12-May-2009
[2168x2]
I dont understand how this prevents the sort of problems I might 
get using global variables?  I was expecting to have to define the 
object inside the function to keep all the variables local to the 
function.
I am thinking that if I take care with these things I will be able 
to reuse fragments of code in lots of projects without worrying that 
I have used the same global variable in two places that conflict.
[unknown: 5]
12-May-2009
[2170x2]
no you must use the /local switch to do that.
func [arg1 arg2 /local lc1 lc2 ...][body...]
mhinson
12-May-2009
[2172]
Paul, how does that relate to using objects please?
[unknown: 5]
12-May-2009
[2173]
Only the things you define in a function as local are local.
PeterWood
12-May-2009
[2174]
Each object has its own context. All variables in the object are 
local to the object's context. Only the object "variable" would be 
in the global context:

>> a: 1

== 1

>> obj: make object! [
[    a: "one"
[    b: "two"
[    c: "three"

[    ]
>> a
== 1
>> obj/a
 
== "one"

>> b

** Script Error: b has no value
** Near: b

>> obj/b
 
== "two"
mhinson
13-May-2009
[2175]
Hi, I have been puzzeling over this all evening & would love a few 
tips please.

I am trying to write a single parse rule that will extract the first 
number before the "/" in each case, but my logic must be faulty I 
think.

digit: charset [#"0" - #"9"]
data1: {random 10/2}
data2: {2/33-35,2/48}

parse/all data1 [ some [[h: 1 2 digit :h copy result to "/" thru 
end] | skip]]
result

parse/all data2 [ some [[h: 1 2 digit :h copy result to "/" thru 
end] | skip]]
result
Oldes
13-May-2009
[2176]
something like this?
digit: charset [#"0" - #"9"]
rest: complement digit
data1: {random 10/2}
data2: {2/33-35,2/48}


parse/all data1 [any [copy x some digit #"/" (probe x) | some digit 
| some rest]]

parse/all data2 [any [copy x some digit #"/" (probe x) | some digit 
| some rest]]
mhinson
13-May-2009
[2177]
PeterWood, thanks for your example. I think I understand too little 
about objects to use them to any benifit yet, I expect it will slowly 
get clearer.
Steeve
13-May-2009
[2178]
or 

parse/all data1 [any [copy x some digit opt [#"/" (probe x)] | skip]]
mhinson
13-May-2009
[2179]
Thanks Oldes, that looks good. I didnt know I could use compliment 
in a parse like that either. I must have been doing it wrong when 
I tried as I kept getting errors. 

Thanks Steeve, I must go & study more about opt too now.   I very 
much appreciate you clever guys coming in this group to help me with 
my simple questions. I am begining to get a bit more productive with 
some of the things I am trying to do, although I am still very much 
a beginner in most areas. Thanks.
mhinson
14-May-2009
[2180]
I just don't "get" Parsing..  I dont understand the syntax & every 
new thing I try takes hours before I chance upon the right syntax. 
 There are so many tutorials & examples that I dont really know which 
one to concentrate my time reading.  When i use OR (|) I get paticularly 
confused as it dosnt seem to evaluate the expressions in order in 
every case.
Janko
14-May-2009
[2181]
you mean parsing with charsets or the "normal" parsing?
mhinson
14-May-2009
[2182x2]
normal I think
Like it took me an hour to work out how to modify Steeve's example 
to only output the first occurance of the match.
Janko
14-May-2009
[2184x2]
aha, that is easier to learn .. I also don't the advanced parsing 
that oldes gave you example, and I wrote a couple of finished programs 
that used "normal" parsing as a main featurea
start with easy examples and go forward from that
mhinson
14-May-2009
[2186x3]
Trouble is that the easy examples dont produce the results I need 
for processing my data :-(
I have spent about 6 hours so far trying to convert this sort of 
format {random 2/2,2/4-6,2/33-37} to module: 2 port: [2 4 5 6 33 
34 35 36 37]  So far even with lots of help I have only managed to 
extract the module number & the ranges, but not the last one because 
there is no comma after it.
I suppose I could add a comma to the end of the string then I would 
be able to use it as a marker.
Janko
14-May-2009
[2189x2]
sometimes an easier solution is possible if you do it in more parse 
runs
or if only comma is the problem slap it at the end and be done with 
it
Henrik
14-May-2009
[2191]
yes, for something like that, I would do some simple splitting to 
get the numbers isolated.
Janko
14-May-2009
[2192]
... from where do you parse 5 out... is that supose NUM-NUM suppose 
to be ranges?
mhinson
14-May-2009
[2193]
so I will add a comma to the end, then parse data [any [ some digit 
#"/" copy result #"," (insert results result) | skip]]
Janko
14-May-2009
[2194]
If it is I wouldn't call that a parse problem, ... remember you have 
to divide and conquer the problems , and that looks like a compound 
problem which parsing is not the big part of.. you just need regular 
"split" method
mhinson
14-May-2009
[2195]
some are ranges & some are single ports
Janko
14-May-2009
[2196]
what does 2 mean in 2/x-y ?
mhinson
14-May-2009
[2197]
the 2 is a module number on a Cisco catos switch
Janko
14-May-2009
[2198]
I qould 1) split on comma to get list of entities  2) for each entity 
if it's a single num append it to block, else split again and append 
 whole range to the block
mhinson
14-May-2009
[2199]
the port information is stored in a form like
set port disable 2/2,2/4,2/6-8
set port disable 3/1-5,3/7
Then the same sort of thing for the names given to the ports.

I want to extract it all into a standard format for analysis & comparison 
of IOS based information (done the IOS stuff ok)
BrianH
14-May-2009
[2200]
a: [...]
some-a-with-comma: [a any ["," a]]
mhinson
14-May-2009
[2201]
CIsco operating systems are IOS or CATOS on switches and output formats 
are very different.
Ladislav
14-May-2009
[2202]
mhinson: the above {copy result #","} does not look intended to me
mhinson
14-May-2009
[2203]
ah, do I need a copy result to perhaps?
Ladislav
14-May-2009
[2204x2]
if {copy result to ...} is what you want then I understand why you 
are having trouble with the END
not-comma: complement charset ","
copy result any [not-comma | skip]