Initialize Array with shape - julia

I want a matrix not the same shape as another matrix, but with the shape the other matrix holds.
shape=[2,3]
matrix=zeros(shape)
size(matrix)=(2,)
How can I get size(matrix)=shape?
I could do it like this:
matrix=zeros(shape[1],shape[2])
is there a more generic way to do it?

try zeros(shape...). The splat operator ... turns a vector into parameters for a function:
v = [a,b,c]
func(v...) # is the same as
func(a,b,c)
and it works for tuples too:
t = (a,b,c)
func(t...) # is the same as
func(a,b,c)

Related

How can I use the apply-Family, when the second function argument is changing along the same dimension as the first argument?

Consider a function f(x,y), where x is a vector (1xn) and data a matrix (nxm), returning a numeric scalar.
Now, I have a matrix A and a three-dimensional array B and would like to apply f across the first dimension of A and B.
Specifically, I would like f to be evaluated at x=A[1,] y=B[1,,], followed by x=A[2,] y=B[2,,] and so on, returning a vector of numeric scalars.
Is there a way to use any function of the "apply" family to solve this problem, thus avoiding a loop?
You can do:
sapply(1:nrow(A), function(i) f(A[i,], B[i,,]))
This is loop hiding because the looping is done inside of sapply(). I suppose in this case it is better to use a explicit loop: 
result <- numeric(nrow(A))
for (i in 1:nrow(A)) result[i] <- f(A[i,], B[i,,]

How to know the index of the iterator when using map in Julia

I have an Array of arrays, called y:
y=Array(Vector{Int64}, 10)
which is basically a list of 1-dimensional arrays(10 of them), and each 1-dimensional array has length 5. Below is an example of how they are initialized:
for i in 1:10
y[i]=sample(1:20, 5)
end
Each 1-dimensional array includes 5 randomly sampled integers between 1 to 20.
Right now I am applying a map function where for each of those 1-dimensional arrays in y , excludes which numbers from 1 to 20:
map(x->setdiff(1:20, x), y)
However, I want to make sure when the function applied to y[i], if the output of setdiff(1:20, y[i]) includes i, i is excluded from the results. in other words I want a function that works like
setdiff(deleteat!(Vector(1:20),i) ,y[i])
but with map.
Mainly my question is that whether you can access the index in the map function.
P.S, I know how to do it with comprehensions, I wanted to know if it is possible to do it with map.
comprehension way:
[setdiff(deleteat!(Vector(1:20), index), value) for (index,value) in enumerate(y)]
Like this?
map(x -> setdiff(deleteat!(Vector(1:20), x[1]),x[2]), enumerate(y))
For your example gives this:
[2,3,4,5,7,8,9,10,11,12,13,15,17,19,20]
[1,3,5,6,7,8,9,10,11,13,16,17,18,20]
....
[1,2,4,7,8,10,11,12,13,14,15,16,17,18]
[1,2,3,5,6,8,11,12,13,14,15,16,17,19,20]

R: possible to use function with two arguments for Map?

What's the right approach to using Map for a function with two arguments in R?
I could get the same effect by using a function which takes 1 argument that consists of a list, and then pass in a list of lists, but I'd like to know if there's a better solution.
Just feed in the extra arguments as a vector like mapply.
Map('+', 1:5, 2:6)
You can name them if you want. If they're not long enough they're recycled out to the right length (e.g. n here)
Map(rnorm, n=1, mean=1:5, sd=1:5)
Since mapply(f, c(a,b,c,...)) = c(f(a), f(b), f(c), ...), it is unclear what those extra arguments should be. If the additional arguments are fixed (or are derived from the element itself), you can use an anonymous function: mapply(function(x) g(1, true, x, 42), c(a,b,c,...)).

How to build out more complex vectorized operations?

I have a sublist of principal component rotation vectors computed by prcomp, where each list item is an Nx2 array (i.e., two column vectors), for each class.
Using those vectors, I'd like to project some data similarly structured into a list of classes, each class item containing arrays with dimension NxMxT, where T is the number of trials.
My problem is, I can write simple vectorized functions with apply and its variants, but I'm having trouble generalizing this to apply that over each list.
Example data:
somedata <- list(array(rnorm(100),dim=c(5,4,5)),array(rnorm(100),dim=c(5,4,5)))
somevectors <- list(array(rnorm(10),dim=c(5,2)),array(rnorm(10),dim=c(5,2)))
Here is a simple example of the operation over each list element:
o.proj.1 <- apply(somedata[[1]],3,function(x){
t(somevectors[[1]]) %*% x
}) # returns an array where each projected trial is a column
I tried fitting this inside a call to lapply(), but didn't find much success:
lapply(somedata, y = somevectors, function(x,y){
apply(x,3,function(z){
t(y) %*% z
})
})
Error in t(y) %*% z : requires numeric/complex matrix/vector arguments
Basically my algorithm is to put the appropriate apply type (here lapply) around the more local function and remove the index that will be vectorized (here [[]]). What am I missing?
Of the *apply family of functions, mapply is the one to use when you want to loop simultaneously over two or more objects. Try:
o.proj <- mapply(function(x,y){
apply(x,3,function(z){
t(y) %*% z
})
}, somedata, somevectors, SIMPLIFY = FALSE)
I suppose you will want to use SIMPLIFY = FALSE to return a list, otherwise mapply will attempt to simplify your output into an array, a little like sapply does.
Also know that you can use Map as a shortcut for mapply(..., SIMPLIFY = FALSE).

R curve() on expression involving vector

I'd like to plot a function of x, where x is applied to a vector. Anyway, easiest to give a trivial example:
var <- c(1,2,3)
curve(mean(var)+x)
curve(mean(var+x))
While the first one works, the second one gives errors:
'expr' did not evaluate to an object of length 'n' and
In var + x : longer object length is not a multiple of shorter object length
Basically I want to find the minimum of such a function: e.g.
optimize(function(x) mean(var+x), interval=c(0,1))
And then be able to visualise the result. While the optimize function works, I can't figure out how to get the curve() to work as well.. Thanks!
The function needs to be vectorized. That means, if it evaluates a vector it has to return a vector of the same length. If you pass any vector to mean the result is always a vector of length 1. Thus, mean is not vectorized. You can use Vectorize:
f <- Vectorize(function(x) mean(var+x))
curve(f,from=0, to=10)
This can be done in the general case using sapply:
curve(sapply(x, function(e) mean(var + e)))
In the specific example you give, mean(var) + x, is of course arithmetically equivalent to what you're looking for. Similar shortcuts might exist for whatever more complicated function you're working with.

Resources