Wondering why I can't use the following code.
enum player_state { fast, slow, focus, bust, out};
if (score >= 100)
player_state = fast;
else if (score > 50)
player_state = slow;
else if ((score <= 50) && (score > 1))
player_state = focus;
else if ((score == 1) || (score < 0))
player_state = bust;
else
player_state = out;
I get an error at the assignment's (=).
any tips? I thought I could do something like this, if not exactly this.
An enum is a type declaration. You have to make a variable that uses that type.
For instance
enum player_states { fast, slow, focus, bust, out};
player_states playerState = fast;
Related
I got the code that compare current element with the next element in array. But it crashes with out of bound because I guess when its on the last element there is no next element to compare with so it crashes.How to handle this to avoid crash and stop comparing on the last element? Here is my code
fun myFunction(arr: Array<Int>): Int{
if (arr.isEmpty()) return 0
var result = 0
for (item in arr.indices) {
if (arr[item] > 0 && arr[item + 1] < 0){
result ++
}
if (arr[item] < 0 && arr[item + 1] > 0){
result ++
}
}
return result
}
The direct answer to your question:
Instead of
for (item in arr.indices)
you should write
for (item in 0..(arr.lastIndex - 1))
Explanation: arr.indices returns the range 0..arr.lastIndex but in the loop you are checking the element after the current index; therefore you should only go up to arr.lastIndex - 1.
Some further advice:
IntArray is more efficient than Array<Int>
You can combine the two if statements into one using the || (or) operator.
If you are counting the number of sign changes, you need to consider how to interpret 0. In your code, an input of [1,-1] would give a result of 1 sign change, but [1,0,-1] would give 0, which seems wrong. To fix that, treat 0 as positive:
if ((arr[item] >= 0 && arr[item + 1] < 0) || arr[item] < 0 && arr[item + 1] >= 0) {
result++
}
You don't need to check if the array is empty; just remove that line. The loop won't be entered if the array is empty or if it has only 1 element.
Finally, you can use some cool features of the standard libray (look them up in the documentation to learn them) which can make your function succinct:
fun myFunction(arr: IntArray): Int {
var result = 0
arr.asList().zipWithNext().forEach { (a, b) ->
if ((a >= 0 && b < 0) || (a < 0 && b >= 0))
result++
}
return result
}
and even more succinct still:
fun myFunction(arr: IntArray) =
arr.asList().zipWithNext().count { (a, b) -> (a >= 0) != (b >= 0) }
References: single-expression functions, zipWithNext, count, destructuring.
I want to do something like this:
if (a < 10) {
println("yes")
} else if (10 < a < 20) {
println("no")
}
apparently I can't do (X < variable < Y)
Sorry if I didn't redacted this so well, hope you get my issue.
Thanks.
First condition a > 10. Second condition a < 20. So you just need to use the "&&" operator that means "and" so it needs to satisfy both conditions.
let a = 15
if a < 10 {
println("yes")
} else if a > 10 && a < 20 {
println("no")
}
In addition to Leonardo Savio Dabus' answer, you can also use contain():
let a = 15
if contains(10...20, a) {
println("no")
}
Just something else you can use. In my opinion it looks a tiny bit better.
This relates to the Coursera Scala course so I want to directly ask you NOT to give me the answer to the problem, but rather to help me debug why something is happening, as a direct answer would violate the Coursera honor code.
I have the following code:
def balance(chars: List[Char]): Boolean = {
val x = 0
def loop(list: List[Char]): Boolean = {
println(list)
if (list.isEmpty) if(x == 0) true
else if (list.head == '(') pushToStack(list.tail)
else if (list.head == ')') if(x <= 0) false else decreaseStack(list.tail)
else loop(list.tail)
true
}
def pushToStack(myList: List[Char]) { x + 1; loop(myList)}
def decreaseStack(myList: List[Char]) { x - 1; loop(myList)}
loop(chars)
}
A simple explanation:
If the code sees a "(" then it adds 1 to a variable. If it sees a ")" then it first checks whether the variable is equal to or smaller than 0. If this is the case, it returns false. If the value is bigger than 0 then it simply decreases one from the variable.
I have tried running the following:
if(balance("This is surely bad :-( ) (".toList)) println("balanced") else println("not balanced");
Clearly this is not balanced, but my code is returning balanced.
Again: I am not asking for help in writing this program, but rather help in explained why the code is returning "balanced" when clearly the string is not balanced
--EDIT--
def balance(chars: List[Char]): Boolean = {
val temp = 0;
def loop(list: List[Char], number: Int): Boolean = {
println(list)
if (list.isEmpty) if(number == 0) true
else if (list.head == '(') loop(list.tail, number + 1)
else if (list.head == ')') if(number <= 0) false else loop(list.tail, number - 1)
else loop(list.tail,number)
true
}
loop(chars,0)
}
^^ Still prints out balanced
You are using an immutable x when you really want a mutable x.
Here, let me rewrite it for you in a tail recursive style to show you what you're actually doing:
#tailrec def loop(myList: List[Char], cur: Int = 0): Boolean = myList match{
case "(" :: xs =>
val tempINeverUse = cur+1
loop(xs, cur) //I passed in 0 without ever changing "cur"!
case ")" :: xs if cur < 0 => false //This is a bug, regardless if you fix the rest of it
case ")" :: xs =>
val tempINeverUse = cur-1
loop(xs, cur) //Passed in 0 again!
case x :: xs => loop(xs, cur)
case Nil => cur == 0 //Since I've never changed it, it will be 0.
}
You need to keep a context of parenthesis in comments or in quotes as well. You can use a counter to achieve that. If the counter is set for a comment or a double quote then ignore any parenthesis that comes your way. Reset the counter whenever you find a finishing comment or double quote
I have this for loop that searches a list for specific values and replaces them with new ones.
for (int i = 0; i < Data.Count; i++) {
if (Data[i] > 0 && Data[i] <= 10) {Data[i] = 1;}
else if (Data[i] > 10 && Data[i] < 20) {Data[i] = 2;}
...
}
I've been trying to write this function in linq and I know it can be written this way:
var Data2 = Data.Where(x=> x > 0 && x <= 10).Select(y=> y=1).ToList();
My question is that is there any way to convert this for loop into linq form without the need to declare new lists? I mean a linq form which searches for these values inside the list and when it finds them it replaces them accordingly.
I would suggest against doing this with LINQ, anyway:
Enumerable.Range(0,Data.Count)
.ForEach(x=>{
if (Data[x] > 0 && Data[x] <= 10) {Data[x] = 1;}
else if (Data[x] > 10 && Data[i] < 20) {Data[x] = 2;}
});
this way you don't have to declare a second list, but the code looks less readeable than your original one.
The exact equivalent would be:
Data
.Select((e,i) => new { Element = e, Index = i })
.Where(ei => ei.Element > 0 && ei.Element < 20)
.ToList()
.ForEach(ei => Data[ei.Index] = (ei.Element <= 10) ? 1 : 2);
or second possibility: look at Save's answer.
However it's still creating a List in-between (ForEach comes only for List<T>). It's not very readable, better to use non-mutable approach and just generate new list basing on given criteria.
A lot simpler than the other solutions:
Data = Data.Select(d => (d / 10) + 1)
If you want a top limit, just use Math.Min((d / 10) + 1, topLimit) instead.
Modifying data in-place is not Linq's strength. Linq methods generally are side-effects free. That is why the .ForEach() method is not a Linq method and is only defined for lists.
However there is nothing preventing you from making Linq functions with side-effects.
So I would not recommend this solution, but you can do anything within a select statement, even modifying the underlying list. There is also a select overload that uses the element and its index as parameters ( Select( (element,index) => ... ).
So you can do anything with select you can do in a for loop. But I would recommend the for loop for readability.
data.Select((d,i)=>
{if (d > 0 && d <= 10) data[i]=1 else if (d>10 && d<20 data[i]=2;})
.All(d=>true); // <-- note that you do need some way to consume the IEnumerable
// in order to execute the .Select(). You can use ToList(), Count(), ..
I am having trouble understanding where the breakpoint is in this do loop. How come the code just doesn't keep running?
def nearest_larger(arr, idx)
diff = 1
loop do
left = idx - diff
right = idx + diff
if (left >= 0) && (arr[left] > arr[idx])
return left
elsif (right < arr.length) && (arr[right] > arr[idx])
return right
elsif (left < 0) && (right >= arr.length)
return nil
end
diff += 1
end
end
Because there are return statements.
Presumably at some point one of the conditions is met and the function exits.
A return statement immediately stops a function, and returns the provided value.
the return keyword is going to stop the running block once it's true