is it possible to use multiple groups with cvpartition in matlab? - matlab

thank you in advance for the input. I am using cvpartition to produce sets that I will use for training and validation on some data. In particular I'm using
c = cvpartition(a,'kfold',5)
where a is a single group. I would like to be able to generate training and testing sets using two groups, say a and b, rather than just a. In other words I'm looking for something like this
c = cvpartition([a b],'kfold',5)
%I haven't tried this; I would like to know ahead of time if this will work
Is this possible to do using cvpartition? If not is there another way that I could easily do this without hard coding a solution?

I was able to find a solution on my own. Albeit not really my desired solution. In my case a and b are integers so I divided a by 10 then added it to b to get a.b. I then used this as my grouping variable. In other words, I created a combined variable that encodes information from a and b, is one to one given a and b, and allows me to use cvpartition to the desired affect.

Related

Working with multiple multiple elements

Say I had y=sin(x) where x is made up of multiple elements, say x=(1:1:5).
How do I solve for all elements in a variable z where all I know is z=cos(y) using just MATLAB code, no algebraic manipulation?
z=cos(sin(x))
Also x=1:5 is enough, no need for increment when it is one

Replace values in an array in matlab without changing the original array

My question is that given an array A, how can you give another array identical to A except changing all negatives to 0 (without changing values in A)?
My way to do this is:
B = A;
B(B<0)=0
Is there any one-line command to do this and also not requiring to create another copy of A?
While this particular problem does happen to have a one-liner solution, e.g. as pointed out by Luis and Ian's suggestions, in general if you want a copy of a matrix with some operation performed on it, then the way to do it is exactly how you did it. Matlab doesn't allow chained operations or compound expressions, so you generally have no choice but to assign to a temporary variable in this manner.
However, if it makes you feel better, B=A is efficient as it will not result in any new allocated memory, unless / until B or A change later on. In other words, before the B(B<0)=0 step, B is simply a reference to A and takes no extra memory. This is just how matlab works under the hood to ensure no memory is wasted on simple aliases.
PS. There is nothing efficient about one-liners per se; in fact, you should avoid them if they lead to obscure code. It's better to have things defined over multiple lines if it makes the logic and intent of the algorithm clearer.
e.g, this is also a valid one-liner that solves your problem:
B = subsasgn(A, substruct('()',{A<0}), 0)
This is in fact the literal answer to your question (i.e. this is pretty much code that matlab will call under the hood for your commands). But is this clearer, more elegant code just because it's a one-liner? No, right?
Try
B = A.*(A>=0)
Explanation:
A>=0 - create matrix where each element is 1 if >= 0, 0 otherwise
A.*(A>=0) - multiply element-wise
B = A.*(A>=0) - Assign the above to B.

Matlab GPU use with functions that take arguments of different dimensions

I am trying to use parallel computing with GPU in Matlab, and I would like to apply a function to a large array (to avoid the use of a for loop, which is quite slow). I have read Matlab's documentation, and I can use arrayfun, but only if I want to do elementwise operations. Maybe I am confused, but I would appreciate if someone can help me to use it. As an example of what I want to do, imagine that I would like to perform the following operation,
$X_t = B Z_t + Q\varepsilon_t$
where $X_t$ is 2x1, $B$ is 2x5, and $Z_t$ is 5x1, with $Q$ 2x2. I define a function,
function X = propose(Z,B,Q)
X=Z*B+Q*rand(2,1);
end
Now, suppose that I have an array $Z_p$ which is 5x1000. To each of the 1000 columns I would like to apply the previous function, for given matrices $B$ and $Q$, to get an array $X_p$ which is 2x1000.
Given the documentation for arrayfun I can not do this,
X=arrayfun(#propose,Zp,B,Q)
So, is there any possibility to do it?
Thanks!
PS: Yes, I know that in this simple example I can just do the multiplication without a for loop, but the application I have in mind is more complicated and I cannot do it. I just put this example as an illustration.

how to 'zero' all variables at each loop iteration

I have written a script describing a dynamic biological process in matlab; the input to which is a year of daily temperature values.The model runs for a year on this daily timestep carrying out different calculations required for the process.
I have thirty years of temperature data (matrix of size 365*30) and I intend to write a 'for loop' at the start of the script in order to use each year of daily data consecutively. I have about 5 variables that are the output from the script, which I intend to output to a txt/csv file at each iteration. My problem is that there are approximately 80 variables within the model and I would like to zero them all at each iteration of the outermost loop (the temperature input). I would like to do this in an efficient manner rather than having to individually zero all the variables. Does anyone know how to do this?
I have been looking at using the 'who' function to list all the variables and I'm thinking that it could be used somehow to zero everything. I have tried letting x = who; which seems to produce a list of all the variables in inverted commas. But obviously; trying to let x = 0 after that just redefines x. I was also thinking of just using 'clear all' but I think this would really slow the model down as it would be 'starting from scratch' redefining all the variable at each loop?
Any help would be appreciated.
First of all, if you have 80 variables you are probably doing something strange. Consider to combine them into vectors or arrays for example.
That being said, there are two situations I can think about:
You already initialize all your variables somewhere
In this case the solution is simple: move the initialization to the start of your outer loop.
You don't initialize anything (bad practice, especially if you are concerned about performance)
In this case you should put a function inside your loop, that only returns your output variables and not all these loose intermediate variables.
Perhaps a combination of these two methods can also apply, but really I would recommend not to use 80 different variables! And initialize any variable that you need to use.
A compact syntax to initialize scalars would be:
[a, b,c] = deal(0);

Finding the difference between columns in matrix without loops

I have the results from an iterative process, where the results from each iteration is placed beside eachother, like this:
res =
43.7826 38.8460 38.6889 38.6912 38.6915
107.0735 98.5577 98.1212 98.1170 98.1175
-134.6218 -131.6938 -131.5378 -131.5352 -131.5352
-105.9498 -103.1403 -102.9195 -102.9139 -102.9139
What I want to do is create one matrix that shows the difference between each column, and one matrix that shows the percentage change from one column to the next.
This is obviously simple to do using loops, but is there a clever way to do this without loops (maybe using some built-in Matlab functions)?
Thanks.
The command diff(...) performes the difference:
diff_res = diff(res,1,2)
in this case the difference of the first order in the second dimension (columns).
After you can compute the percentage:
per_res = diff_res(:,1:4)./res(:,1:4).*100