I'm new to scala and I'm trying to figure out how tuple works. I'm trying to call the xth element of a tuplle where x is a variable but it seems not to work, how should I do?
for (x <- 1 to 2; j <- 0 to (N-1)) yield((j, index._x), (x-1,index._x))
In particular the index._x seem to not work
It is possible to do this using the Product trait, though, as mentioned in the comment, this is not really a good idea or the intended way tuples are supposed to be used:
val indexed = index.productIterator.toIndexedSeq
for {
x <- 1 to 2
j <- 0 until N
} yield ((j, indexed(x-1)), (x-1, indexed(x-1))
or better yet (get rid of indexed access, it's yuky):
index.productIterator.take(2).toSeq.zipWithIndex
.flatMap { case (value, index) =>
(0 until N).map { j => ((j, value), (index, value)) }
}
I'll say it again though: there is about 99% chance there is a better way to do what you are actually trying to do. Tuples are meant for grouping data, not iterating over it (use collections for that).
Related
I am using a for comprehension on a stream and I would like to know how many iterations took to get o the final results.
In code:
var count = 0
for {
xs <- xs_generator
x <- xs
count = count + 1 //doesn't work!!
if (x prop)
yield x
}
Is there a way to achieve this?
Edit: If you don't want to return only the first item, but the entire stream of solutions, take a look at the second part.
Edit-2: Shorter version with zipWithIndex appended.
It's not entirely clear what you are attempting to do. To me it seems as if you are trying to find something in a stream of lists, and additionaly save the number of checked elements.
If this is what you want, consider doing something like this:
/** Returns `x` that satisfies predicate `prop`
* as well the the total number of tested `x`s
*/
def findTheX(): (Int, Int) = {
val xs_generator = Stream.from(1).map(a => (1 to a).toList).take(1000)
var count = 0
def prop(x: Int): Boolean = x % 317 == 0
for (xs <- xs_generator; x <- xs) {
count += 1
if (prop(x)) {
return (x, count)
}
}
throw new Exception("No solution exists")
}
println(findTheX())
// prints:
// (317,50403)
Several important points:
Scala's for-comprehension have nothing to do with Python's "yield". Just in case you thought they did: re-read the documentation on for-comprehensions.
There is no built-in syntax for breaking out of for-comprehensions. It's better to wrap it into a function, and then call return. There is also breakable though, but it works with Exceptions.
The function returns the found item and the total count of checked items, therefore the return type is (Int, Int).
The error in the end after the for-comprehension is to ensure that the return type is Nothing <: (Int, Int) instead of Unit, which is not a subtype of (Int, Int).
Think twice when you want to use Stream for such purposes in this way: after generating the first few elements, the Stream holds them in memory. This might lead to "GC-overhead limit exceeded"-errors if the Stream isn't used properly.
Just to emphasize it again: the yield in Scala for-comprehensions is unrelated to Python's yield. Scala has no built-in support for coroutines and generators. You don't need them as often as you might think, but it requires some readjustment.
EDIT
I've re-read your question again. In case that you want an entire stream of solutions together with a counter of how many different xs have been checked, you might use something like that instead:
val xs_generator = Stream.from(1).map(a => (1 to a).toList)
var count = 0
def prop(x: Int): Boolean = x % 317 == 0
val xsWithCounter = for {
xs <- xs_generator;
x <- xs
_ = { count = count + 1 }
if (prop(x))
} yield (x, count)
println(xsWithCounter.take(10).toList)
// prints:
// List(
// (317,50403), (317,50721), (317,51040), (317,51360), (317,51681),
// (317,52003), (317,52326), (317,52650), (317,52975), (317,53301)
// )
Note the _ = { ... } part. There is a limited number of things that can occur in a for-comprehension:
generators (the x <- things)
filters/guards (if-s)
value definitions
Here, we sort-of abuse the value-definition syntax to update the counter. We use the block { counter += 1 } as the right hand side of the assignment. It returns Unit. Since we don't need the result of the block, we use _ as the left hand side of the assignment. In this way, this block is executed once for every x.
EDIT-2
If mutating the counter is not your main goal, you can of course use the zipWithIndex directly:
val xsWithCounter =
xs_generator.flatten.zipWithIndex.filter{x => prop(x._1)}
It gives almost the same result as the previous version, but the indices are shifted by -1 (it's the indices, not the number of tried x-s).
I want to generate a Vector of tuple of two Ints. For now, I do as follows:
(0 until 100).map(x => (x+1 until 100).map(y => (x,y))).flatten.filter { ... }
I wondered if there were any more efficient way to do this. I have the feeling that "flatten" slows down the code. Do I have to use "flatten" or can I use something else ?
PS1: If I don't use "flatten", I have: Vector(Vector(a,b),Vector(c,d),...) and not Vector((a,b),(c,d),...).
PS2: I use (x+1 until 100) in the second generator as I'm not interested in having tuples (a,b) and (b,a).
for {
i <- 0 until 100
j <- i+1 until 100
} yield (i,j)
map(f).flatten can be shortened to flatMap(f), so you'll get
(0 until 100).flatMap(x => (x+1 until 100).map(y => (x,y))).filter(...)
This is equivalent to Tzach Zohar's answer, but you can see the relation. It may also be worthwhile to move filter inside flatMap (it will get called more times, but you'll get smaller intermediate collections).
Is there a way I can perform a faster computation of upper triangle matrix in scala?
/** Returns a vector which consists of the upper triangular elements of a matrix */
def getUpperTriangle(A: Array[Array[Double]]) =
{
var A_ = Seq(0.)
for (i <- 0 to A.size - 1;j <- 0 to A(0).size - 1)
{
if (i <= j){
A_ = A_ ++ Seq(A(i)(j))
}
}
A_.tail.toArray
}
I don't know about faster, but this is a lot shorter and more "functional" (I note you tagged your question with functional-programming)
def getUpperTriangle(a: Array[Array[Double]]) =
(0 until a.size).flatMap(i => a(i).drop(i)).toArray
or, more or less same idea:
def getUpperTriangle(a: Array[Array[Double]]) =
a.zipWithIndex.flatMap{case(r,i) => r.drop(i)}
Here are three basic things you can do to streamline your logic to improve performance:
Start with an empty Seq, so you don't have to call Seq.tail at the end. The tail operation is going to be O(n), since the Seq factory methods give you an IndexedSeq
Use Seq.:+ to append a single element to the Seq, instead of constructing a Seq with a single element, and using Seq.++ to append two Seqs. Seq.:+ is going to be O(1) (amortized) and quite fast for an IndexedSeq. Using Seq.++ with a single-element sequence is probably still O(1), but will have a good bit more overhead.
You can start j at i instead of starting j at 0 and testing i <= j in the body of the loop. This will save n^2/2 no-op loop iterations.
Some stylistic things:
It's best to always include the return type. You actually get a deprecation warning without it.
We use lowercase for variable names in Scala
0 until size is perhaps more readable than 0 to size - 1
def getUpperTriangle(a: Array[Array[Double]]): Array[Double] = {
var result = Seq[Double]()
for (i <- 0 until a.size; j <- i until A(0).size) {
result = result :+ a(i)(j)
}
result.toArray
}
In Scala, for and for-yield loops are usually translated to a squence of map, flatMap and filter calls with Lambdas. Since the compiler converts there Lambdas into Anonymous Classes instead of Java 8's fancy invokedynamic / LambdaMetafactory / Unsafe.defineAnonymousClass system. This obviously creates a lot of overhead for the temporary classes and their instances, as well as the overhead of the map, flatMap and filter operations, which usually copy their underlying collections. Is there any particular reason to use the functional approach to a problem when the generally faster iterative approach is available, at least on the bytecode level?
For example, why does
for {
sl <- l
el <- sl
if el > 0
} println el.toString.length
translate to
l.flatMap(sl => sl.filter(el => el > 0).foreach(el => println el.toString.length))
Instead of
for (sl <- l) // Iterable for loop
{
for (el <- sl) // Iterable for loop
{
println el.toString.length
}
}
It's implemented that way because that's how the SLS defines it. The rules are rather large to paste here, but they're fully included in the spec.
For Comprehensions and For Loops
Example
The following code produces all pairs of numbers between 1 and
n−1 whose sums are prime.
for { i <- 1 until n
j <- 1 until i
if isPrime(i+j)
} yield (i, j)
The for comprehension is translated to:
(1 until n)
.flatMap {
case i => (1 until i)
.withFilter { j => isPrime(i+j) }
.map { case j => (i, j) } }
I am currently learning scala. I am reading Scala for the impatient.
1.)
Guards
Is there a difference?
for (i <- 0 to 10)if (i % 2 == 0) println(i)
for (i <- 0 to 10 if i % 2 == 0) println(i)
2.)
I always see the following symbol => but they never explain what it does.
Sometimes I think it is a cast but then it is something completely different, I hope you can clear things up.
1.) Yes, there is a difference, the first if a normal if statement inside of the closure you pass to the for-comprehension. The second is an actual guard. It will actually call withFilter on the range, before calling foreach. So the translation of the two things will look like this:
0.to(10).foreach(i => if(i % 2 == 0) println(i) )
0.to(10).withFilter(x => x % 2 == 0).foreach(i => println(i))
To add a little more context, calling withFilter or even just filter instead of using a normal if statement has some benefits. In a for comprehension, you can have nested calls to map, flatmap, filter, collect etc. so if you add guards, you can prevent a lot af calls from actually happening. For example:
for {
x <- 0 until 10
y <- 10 until 20
} {
if(x % 2 == 0) println(x*y)
}
would call the actual closure 100 times
for {
x <- 0 until 10
if x % 2 == 0
y <- 10 until 20
} println(x*y)
this will only call it 50 times, while the result stays the same.
2.)
=> separates the argument list of a function/closure from the body.
This case e: NumberFormatException => None is a part of a partial function. Here the => separates the "argument" e from the body None.
In a type signature like in someFunction(i: (A) => Int) it implies that i is of the type Function1[A,Int], read "function from A to Int".