You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I've been experimenting with the idea that when functions are used in circumstances like this, that the parameter be via refinement... and whether the parameter is passed depends on if the refinement is in the spec.
The thing is that there might be a "stateful" function that already knows how many times it has been called, and forcing a parameter could complicate it to needing to write an adapter. So my idea is more like allow both:
"Sniffing" for the capability to take a refinement is not something that is made particularly easy today, but as with many things, it could be made easier.
This is all ignoring the name "ARRAY" which is a separate question. :-)
Rebolbot commented on Feb 22, 2015:
Submitted by:BrianH
ARRAY can generate multidimensional blocks, so the index passed should be either a direct index for single dimensions or a block of indexes for multiple dimensions; or, for usability, pass in the same number of parameters as there are dimensions using a composed argument to APPLY.
We will probably need to use APPLY anyway, since the current model isn't very op!-friendly, and we want the actual arity and evaluation model of the function's arguments to be ignored so our code is more robust. It gets trickier when you consider that the multi-dimensional arrays are composed with recursive calls to ARRAY, which would probably require some kind of intermediate function to be passed which curries parameters if we continue to do it this way. We should see if there's an efficient way to do this.
Still, this seems like a good idea. The way we handled this usage model was to have the passed function do a counter as a side effect. Something that works with pure functions would be preferable.
(The above was completely ignoring Fork's refinement suggestion, since APPLY can handle optional arguments without needing a refinement in the function.)
Rebolbot commented on Feb 23, 2015:
Submitted by:BrianH
OK, I figured out a reasonably efficient implementation of this. It passes the indexes of the current element to the value function in the order specified with the size block, but calls that function with APPLY so the function doesn't necessarily have to take those index arguments, since APPLY ignores evaluation modes and arity, padding missing arguments with nones. It uses an internal function option for the recursive calls, but it enforces internal use of that option by using a bound tag word argument.
array: func["Makes and initializes a series of a given size."
size [integer!block!] "Size or block of sizes for each dimension"/initial"Specify an initial value for all elements"
value {Initial value (will be called each time if a function)}/local block rest word
/with tag indexes
] [
unless same? :tag 'tag [with:tag:indexes: none] ; Enforced internalif block? size [
ifall [not with any-function? :value] [
indexes:append/dup make block!2* length? size [index? block] length? size
]
if tail? rest:next size [rest: none]
unless integer? set/any 'size first size [
cause-error 'script 'expect-arg reduce ['array 'size type?:size]
]
]
block: make block! size
case [
block? :rest [
either any-function? :value [
word:in make object! copy [x: block] 'x
indexes: change next indexes word
loop size [
set word insert/onlyget word array/initial/with rest :value 'tag indexes
]
block:get word
] [
loop size [block:insert/only block array/initial rest :value]
]
]
series? :value [
loop size [block:insert/only block copy/deep value]
]
any-function? :value [
unless indexes [indexes: [index? block]]
loop size [block:insert/only block apply :valuehead indexes]
]
insert/dup block value size
]
head block
]
Submitted by: rebolek
ARRAY/INITIAL accepts a function. I think that it should pass index to that function so the function would be much more useful.
Old code:
New code:
Imported from: CureCode [ Version: r3 master Type: Wish Platform: All Category: Mezzanine Reproduce: Always Fixed-in:none ]
Imported from: metaeducation#2193
Comments:
Submitted by: fork
I've been experimenting with the idea that when functions are used in circumstances like this, that the parameter be via refinement... and whether the parameter is passed depends on if the refinement is in the spec.
The thing is that there might be a "stateful" function that already knows how many times it has been called, and forcing a parameter could complicate it to needing to write an adapter. So my idea is more like allow both:
"Sniffing" for the capability to take a refinement is not something that is made particularly easy today, but as with many things, it could be made easier.
This is all ignoring the name "ARRAY" which is a separate question. :-)
Submitted by: BrianH
ARRAY can generate multidimensional blocks, so the index passed should be either a direct index for single dimensions or a block of indexes for multiple dimensions; or, for usability, pass in the same number of parameters as there are dimensions using a composed argument to APPLY.
We will probably need to use APPLY anyway, since the current model isn't very op!-friendly, and we want the actual arity and evaluation model of the function's arguments to be ignored so our code is more robust. It gets trickier when you consider that the multi-dimensional arrays are composed with recursive calls to ARRAY, which would probably require some kind of intermediate function to be passed which curries parameters if we continue to do it this way. We should see if there's an efficient way to do this.
Still, this seems like a good idea. The way we handled this usage model was to have the passed function do a counter as a side effect. Something that works with pure functions would be preferable.
(The above was completely ignoring Fork's refinement suggestion, since APPLY can handle optional arguments without needing a refinement in the function.)
Submitted by: BrianH
OK, I figured out a reasonably efficient implementation of this. It passes the indexes of the current element to the value function in the order specified with the size block, but calls that function with APPLY so the function doesn't necessarily have to take those index arguments, since APPLY ignores evaluation modes and arity, padding missing arguments with nones. It uses an internal function option for the recursive calls, but it enforces internal use of that option by using a bound tag word argument.
Here's an example of its use:
Submitted by: BrianH
PR: rebol/rebol#235
The text was updated successfully, but these errors were encountered: