Is there a method for running multiple case statements (say 2 out of 3) in a MATLAB switch? Or do I have to use a series of if statements? I would like do something similar to:
test = {'test1','test2'}
switch test
case 'test1'
disp('test1')
case 'test2'
disp('test2')
case 'test3'
disp('test3')
end
Output:
test1
test2
On a side note: is there any way to parallelize such code so that the different cases can be run simultaneously?
the if statement would be more appropriate if you 1/ want to test for multiple cases 2/parallelize.
something like
if ismember('test1',test)
%code
end
if you want to make it parallel, you can do it through the following:
test is your data, case is the cell containing all possiblities
parfor(i=1:length(cases)){ %you need to parse the cases not the data
if(ismember(case{i},test)){
%code
}
}
A solution can be put the switch into a function and then use the cellfun. Hence, define the function:
function a = func(test)
switch test
case 'test1'
disp('test1')
case 'test2'
disp('test2')
case 'test3'
disp('test3')
end
end
then, apply to the test:
cellfun(#func, test)
The result would be:
test1
test2
Related
NOTE: this question is not asking for help solving FizzBuzz. Please don't post answers that just solve FizzBuzz. Answers to this question should relate to matching multiple true switch cases
Consider an attempted FizzBuzz solution in Swift using a switch statement:
func fizzBuzz(forInt int: Int) -> String {
var output = ""
switch 0 {
case (int % 3): output += "Fizz"
case (int % 5): output += "Buzz"
default:
output = String(int)
}
return output
}
// FAILS
assert(fizzBuzz(forInt: 15) == "FizzBuzz", "15 should output `FizzBuzz`, not `Fizz`!")
The correct output on iteration 15 should be "FizzBuzz" because 15 is divisible by both 3 and 5.
But the program above outputs "Fizz" because only the first passing case is executed.
The Swift docs state:
A switch statement executes an appropriate block of code based on the first pattern that matches successfully.
It seems that it would be useful for there to be a similar, switch-like statement that matches any true case rather than just the first.
Pattern matching patterns can currently be used in the following situations:
You use these patterns in a case label of a switch statement, a catch clause of a do statement, or in the case condition of an if, while, guard, or for-in statement.
Matching multiple patterns seems impossible in Swift. Options considered:
fallthrough
Switch fallthrough allows one executed case to fall into and execute the physically next case, but without actually testing the case statement. It does not allow multiple, arbitrary, unordered cases to be executed only if matching.
multiple if statements
Multiple if statements produce the desired behavior, but are annoying for the same reasons switch is often preferred over if-else blocks.
if (i % 3 == 0) {
// ...
}
if (i % 5 == 0) {
// ...
}
Namely re-stating the variable being tested in each case, no compiler protection that we're evaluating the same single variable against multiple cases, etc.
tuples, etc.
Yes, it's possible to do things like switch on a tuple to produce the correct output value. But that involves duplicating code inside the cases.
switch (i % 3, i % 5) {
case (0, 0):
output += "FizzBuzz"
case (0, _):
output += "Fizz"
case (_, 0):
output += "Buzz"
The goal of this question is to have only 2 cases for "Fizz" and "Buzz". Combined execution of the true cases should produce "FizzBuzz", not a separate 3rd case that duplicates the strings.
Related:
Switch to match multiple cases from OptionSetType
Question:
Does there exist a switch-like pattern matching control flow statement that matches any and all true cases? If not in Swift, do any languages contain such a feature?
This loop-nested switch syntax executes each true case in order, not just the first true case.
for i in 1...100 {
var output = ""
for eachCase in 0...1 {
switch (eachCase, 0) {
case (0, i % 3): output += "Fizz"
case (1, i % 5): output += "Buzz"
default: break }
}
if output.isEmpty {
output = String(i)
}
print(output)
}
I'll leave it to the reader to determine situations where this is better behavior than alternative such as multiple if statements.
There was a Swift evolution proposal to introduce a continue statement within Switch cases, which would resume pattern matching against the remaining cases.
[swift-evolution] [Pitch] Introduce continue to switch statements
This proposal completes the switch statement's control flow transfer suite by introducing continue. This change adds functionality that many developers expect (but do not get) from fallthrough.
https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160704/023955.html
https://gist.github.com/erica/04835de3d3d9121ef7308dd9b093158a
Introducing continue means "resume pattern matching after executing this case clause". It offers more nuanced control than currently exists within switch.
This code in lua will apply a function to a value
function Apply(f, value)
return f(value)
end
I can then use it like this apply arbitrary functions calls on my game object like so
Apply(Draw, GameObject)
Apply(Update, GameObject)
Is it possible to instead do what I would, probably incorrectly, call a higher order method
function GameObject:Apply(f)
return self:f()
end
What I eventually want to do is have a table of GameObjects, that I can call Methods on in batch. So using this "higher order method" concept that may not even exist I would create code that does the following.
...
--Create the batch object with three bullets in it
BatchGameObjects = BatchGameObject:new(Bullet1, Bullet2, Bullet3)
--Call equivelent to
--Bullet1:DrawMethod()
--Bullet2:DrawMethod()
--Bullet3:DrawMethod()
--Bullet1:UpdateMethod()
--Bullet2:UpdateMethod()
--Bullet3:UpdateMethod()
BatchGameObjects:Apply(DrawMethod)
BatchGameObjects:Apply(UpdateMethod)
You'll probably want to pass function NAME if you're dealing with methods on other objects, because methods with same name on different objects may resolve to very different functions.
function BatchGameObjects:Apply(function_name)
-- ... or iterate on objects in any other way that matches how you store them ...
for idx = 1, #self.object_list do
local object = self.object_list[idx]
object[function_name](object)
end
end
function GameObject:Apply(f)
return f(self)
end
In PostgreSQL this is a valid query:
SELECT case 2+2 when 1 then 2 else 3 end
If I put a complex subquery instead of '2+2' it still works well. But how can I change this query if i want to know if the result is smaller than a specific number?
For example this one doesn't work:
SELECT case 2+2 when > 1 then 2 else 3 end
There are two forms of the CASE statement in SQL, described in the PostgreSQL manual here.
One, which you are using, compares a particular expression to a series of values, like a switch statement in C or PHP:
CASE something WHEN 1 THEN 'hello' ELSE 'goodbye' END
The other is a more general set of branching conditions, like an if-elseif-else sequence, or PHP's switch(true). The above can also be written like this:
CASE WHEN something = 1 THEN 'hello' ELSE 'goodbye' END
So to use any comparison other than =, you need the "if-like" version. In your example:
SELECT CASE WHEN 2+2 > 1 THEN 2 ELSE 3 END
select case when 2+2 > 1 then this else that end
I'm trying to write a function that puts the class, length, and value of each of the things in a cell array into a struct, but I keep getting an error with the switch statements
function [ out, common ] = IDcell( cA )
%UNTITLED Summary of this function goes here
% Detailed explanation goes here
cl={};
val={};
len={};
for x=1:length(cA)
switch cA(x)
case isnum
cl(x)='double';
case ischar
cl(x)='char';
case islogical
cl(x)='logical';
case iscell
cl(x)= 'cell';
end
val=[val cA{x}];
len=[len size(value(x))];
end
out=struct('value', val, 'class', cl, 'length', len);
end
[out]=IDcell(cA)
SWITCH expression must be a scalar or string constant.
Error in IDcell (line 8)
switch cA(x)
isnum is not a Matlab function. isnumeric may be what you were thinking of, but it isn't what you typed. Which means your code is seeing case isnum and it has no idea what the heck isnum is, so it is telling you whatever it is, if you want to use it there you need to make it something that evaluates to a number (what it means by scalar) or to a piece of text (what it means by string constant).
Further, ischar is a matlab function, but you are not using it the right way. You must use it as ischar(cA(x)) for example, will then evaluate to true if cA(x) is a string or snippet of text, will evaluate to false if cA(x) is anything else.
While it would be lovely if switch worked this way, it doesn't. You can't put a thing in the switch part, and then just list functions that need to be evaluated on that thing in the switch part.
The kind of thing you can do is this:
switch class(x)
case 'double'
fprintf('Double\n');
case 'logical'
fprintf('Logical\n');
end
Here I have used the class function the way it needs to be used, with an argument in it. And I then switch my cases based on the output of that function, class outputs a string.
How can I break/continue nested loops in Coffeescript? E.g. I have something like:
for cat in categories
for job in jobs
if condition
do(this)
## Iterate to the next cat in the first loop
Also, is there a way to wrap the whole second loop as a conditional to another function within the first loop? E.g.
for cat in categories
if conditionTerm == job for job in jobs
do(this)
## Iterate to the next cat in the first loop
do(that) ## Execute upon eliminating all possibilities in the second for loop,
## but don't if the 'if conditionTerm' was met
break works just like js:
for cat in categories
for job in jobs
if condition
do this
break ## Iterate to the next cat in the first loop
Your second case is not very clear, but I assume you want this:
for cat in categories
for job in jobs
do this
condition = job is 'something'
do that unless condition
Use labels. Since CoffeeScript doesn't support them, you need to hack as such:
0 && dummy
`CAT: //`
for cat in categories
for job in jobs
if conditionTerm == job
do this
`continue CAT` ## Iterate to the next cat in the first loop
do that ## Execute upon eliminating all possibilities in the second for loop,
## but don't if the 'if conditionTerm' was met
Coffescript's "break" only breaks the immediate loop and has no way of identifying an outer loop for breakage (annoying!). This following hack works in some instances for breaking out of multiple loops when a condition is met:
ar1 = [1,2,3,4]
ar2 = [5,6,7,8]
for num1 in ar1
for num2 in ar2
console.log num1 + ' : ' + num2
if num2 == 6
breakLoop1 = true; break
break if breakLoop1
# Will print:
# 1 : 5
# 1 : 6
Using anonymous loop with return
do ->
for a in A
for b in B
for c in C
for d in D
for e in E
for f in F
for g in G
for h in H
for i in I
#DO SOMETHING
if (condition)
return true
Coffeescript would never have multiple breaking/continuing statements, you have to stick to ugly and excessive flags polluting your code or try to replace it by do with a lambda and use return as a multiple break.
https://github.com/jashkenas/coffeescript/issues/4254
For checking all elements in an array, maybe lodash's every would be of use?
https://lodash.com/docs#every
for cat in categories
if _.every jobs, conditionTerm
...
I suppose the design of your code is not very good if you want to use inner break/continue.
It seems to me that any programming language doesn`t allow that.
Using labels as someone suggested is also considered as bad style.