In this blog I'll post on everything thats going on with my games, I'm developing. There may be some more things, but thats the main topic.
A project I've worked on is for example WorldOfCube, download here:
Download.

28th May 2014

Post

Tinkering with Haskell

So today I sat in school. We learned about Floating Point numbers.

When the teacher finished explaining of what these data-types consisted of in terms of bits, he wanted us to try out an example and convert the number 36.76 into IEEE 555 Float bits.

To do that we had to first convert 36 to binary, then 0.76 to binary and then find out what the exponent should be, so that the number was in the form of (-1)s * 1.m * 2e - 127

Okay. Fine. So converting 36 to binary works like this: You divide the number by the base you want to convert to (in this case 2 for binary) note the quotient and remainder and repeat the process with the remainder until you have 0 as a quotient.

It’d look like this for 36:

36 / 2 = 18 remainder 0
18 / 2 = 9  remainder 0
9  / 2 = 4  remainder 1
4  / 2 = 2  remainder 0
2  / 2 = 1  remainder 0
1  / 2 = 0  remainder 1

So now you note the number from left to right by reading the remainders from bottom to top: 100100, which is, in fact, the binary representation of the number 36.

It’s not like we did this the first time, though. We had to do this conversion not only just with the number 36, but also with other numbers and into other bases like for example converting 42 into base 16 (hexadecimal) or base 8 (octal).

So I was a little fed up with it and wanted to write a program for doing that for me. Luckily I had installed a portable GHC and GHCI for writing haskell code on my school computer ;)

I came up with this:

module Bases where

convert :: Int -> Int -> [Int]
convert _    0      = []
convert base number = (convert base quotient) ++ [remainder]
  where (quotient, remainder) = number `quotRem` base

The thing I liked about the function was it’s simplicity.

When reading the type signature :: Int -> Int -> [Int] a haskeller can easily find out how the function needs to be used. In this case the function expects two integer arguments, “Int”s. The first argument is the base for the number to be converted to and the second argument is the number to be converted. The resulting data is a list of Ints, for example [1,0,0,1,0,0] is the result for the application convert 2 36 (convert to base 2 the number 36).

It also works for other bases, for example base 16:

(ghci log:)
λ> convert 16 36
[2,4]
λ> convert 16 123456789
[7,5,11,12,13,1,5]

Maybe you didn’t expect something like “11” to pop up, but it’s just the information that it’s the 11th digit of the base. In hexadecimal people have agreed on using A for the 10th, B for the 11th etc. So that’s maybe what you’d expect to pop up: 75BCD15.

The Algorithm

The algorithm works exactly the same like our method with dividing the number by the base.

For divisions of numbers while at the same time getting both the quotient and the remainder, haskell has the function called quotRem. Each part of the return value can be taken apart by something called “Pattern Matching”: (quotient, remainder) = number `quotRem` base (I used `these` to tell haskell that I use the function as infix function. Usually I’d have to write (quotinet, remainder) = quotRem number base))

So now I could move to implementing the algorithm. We learned the following rules for converting the numbers into any base:

  1. Divide the number by the base and note the remainder. Repeat that with the quotient.
  2. Except when the quotient is 0. Then you can stop.

These rules were obviously recursive: Rule 1 goes back to Rule 1 or Rule 2, depending on the quotient. You could simply write down Rule 1 almost like it was defined like this:

convert base number = convert base quotient [and note] remainder

So this obiously doesn’t work like that in haskell. We’ll leave the “noting” or “remembering” of the remainder out for now and focus on how to get the quotient and remainder. It’s quite simple when using quotRem:

convert base number = convert base quotient [and note] remainder
  where (quotient, remainder) = number `quotRem` base

Nice! So that’s sorted out now. Now for “remembering” the remainders we simply use a list in which we accumulate the results:

convert base number = (convert base quotient) ++ [remainder]
  where (quotient, remainder) = number `quotRem` base

(++ connects two lists, for example: [1,2,3] ++ [4,5,6] == [1,2,3,4,5,6], [remainder] is a list with one element being the value of the variable “remainder”)

So now we only need to add the first rule, which is extremely simple:

convert _    0      = []
convert base number = (convert base quotient) ++ [remainder]
  where (quotient, remainder) = number `quotRem` base

And now we’re at our starting example.

Numbers after the Decimal Point

For converting the numbers after the decimal point we learned another little set of rules. Converting the number 0.76 to binary looked like this:

0.76 * 2 = 1.52, note 1
0.52 * 2 = 1.04, note 1
0.04 * 2 = 0.08, note 0
0.08 * 2 = 0.16, note 0
0.16 * 2 = 0.32, note 0
0.32 * 2 = 0.64, note 0
0.64 * 2 = 1.28, note 1
0.28 * 2 = 0.56, note 0
...

Which is now read the other way around, from top to bottom and gives: 11000010... and more digits. This number can’t be represented in binary, just like the fraction 1/3 can’t be shown in decimal (0.33333333…), they’re recurring.

These rules can also be implemented in haskell. To get the number in front of the decimal point of another number, we can use the function “floor” (floor 3.45 == 3, floor 2.22 == 2, floor 0.123 = 0).

In code, this function looks like this:

convertComma :: Int -> Double -> [Int]
convertComma _    0      = []
convertComma base number = floored : (convertComma base reduced)
  where
    multiplied = number * (fromIntegral base)
    floored = floor multiplied
    reduced = multiplied - (fromIntegral floored)

(: is used for prepending an element to a list, so 1:[1,2] == [1,1,2], 1:2:3:4:[] == [1, 2, 3, 4], you can leave out fromIntegral when reading this code for now))

Understanding this function is left as an exercise for the reader ;)

The fact why it is very interesting is the problem of recurring numbers.

Let’s try it out: (using the final version now (the generalized one), sorry, sadly this doesn’t work for “Double”s)

λ> convertComma 2 (1 % 123)
[0,0,0,0,0,0,1,0,0,0,0,1,0,1,0,0,1,1,0,1,0,0,0,
0,0,0,1,0,0,0,0,1,0,1,0,0,1,1,0,1,0,0,0,0,0,0,1,
0,0,0,0,1,0,1,0,0,1,1,0,1,0,0,0,0,0,0,1,0,0,0,0,
1,0,1,0,0,1,1,0,1,0,0,0,0,0,0,1,0,0,0,0,1,0,1,0,
0,1,1,0,1,0,0,0,0,0,0,1,0,0,0,0,1,0,1,0,0,1,1,0,
1,0,0,0,0,0,0,1,0,0,0,0,1,0,1,0,0,1,1,0,1,0,0,0,
0,0,0,1,0,0,0,0,1,0,1,0,0,1,1,0,1,0,0,0,0,0,0,1

(1 % 123 is a fraction)

As you can see, GHCI shoots us with zeroes and ones. During that school lesson I was fascinated. It looked so awesome :D

This is simply because 1 / 123 is a recurring number in binary (maybe you can spot the pattern?).

Duh, haskell is so lazy

A normal programmer would expect such a program to run forever, but never actually print a result. GHCI only prints out the result that it was given from the computation. We can simulate that like this:

λ> print $ convertComma 2 (1 % 123)
[0,0,...

But print actually only runs, as soon as what it was given has been computated, that is convertComma 2 (1 % 123). So how can print start to print it, even though convertComma should actually never return?

It’s due to laziness. Haskell is lazy. What does that mean? When haskell finds the expression 5 + 1 it doesn’t start computing it, but instead, remembers 5 + 1.

So when you execute print $ convertComma 2 (1 % 123), print asks for the first element of the list, which is then calculated but not further. Only when print asks for the second element, it starts to calculate the second, etc.

So what the function “convertComma” returns, is in some cases an infinite list of numbers. Another example for an infinite list of numbers is [1..], which simply counts up. That one gives quite a funny pattern when executed and printed in GHCI.

Laziness is really useful. If we, for example, wanted a function that returns not the list directly, but a string with A substituted for 10 and B for 11 and so on, just like it’s convention for hexadecimals, then, given a function printDigit, we could change our code to this:

λ> map printDigit (convertComma 16 (1 % 123))
"0214D0214D0214D0214D0214D0214D0214D0214D0214...

(map applies the function “printDigit” to every element of the list)

And it’s still printed, even though the string (in this case) is infinite.

Generalizing

We haven’t heard anything about type signatures for a long time now… But they’re actually one of the key things I like in haskell. It’s hard to explain, why type signatures are so useful, the best explanation I can think of is:

The computer should be able to help you find errors / bugs in your code, no matter how trivial they are, before you have run the code even once, because it can.

Haskell has something called a “type-checker”. Those make sure that the types match up in your programs between what a function expects and what it’s given as arguments.

For example, a type-checker would prevent the following from happening or even compiling:

floor "lol"

The easiest way to get, why this simply can’t work is look at the type signatures of both values floor and "lol":

-- This is simplified!
floor :: Double -> Int
"lol" :: String

(you can find out the type of an expression in GHCI by typing, for example :type "lol". This will print out [Char], which is right. A String is nothing more but a list of individual characters. Though, it’s convenient to have a String-type. Therefore haskell has a type-alias for String: type String = [Char].)

And now you can see that the String “lol” doesn’t fit into the Double Slot of floor. The type-checker sees that and corrects it.

This was a trivial example, but there are better examples, which in turn require more context information, though. If you ever heard about mathematical proofs, I’ll blow your mind: Type signatures are - in a way - propositions for the proofs, which lie in the code itself. The axioms of this system are the primitive functions of the runtime system, in this case the primitive functions of haskell.

If you didn’t understand that, don’t worry. Just revisit this statement a while later, when you’ve maybe learned about haskell more and maybe more about mathematical proofs. This is called the curry-howard isomorphism or the curry-howard correspondence, btw.

So back to the basics. Our example of converting numbers into any-base number lists only works with Ints. That’s a problem. Ints have a 31-bit positive precision. That means their maximal value can’t exceed 231, but maybe someone wants to convert a Long into binary, which has 63-bit positive precision?

Now Ints and Longs are kind of similar: They share possible operations: They can be added, subtracted and similar, they only differ in the precision. So that could be simplified.

Haskell has something they call “Type Classes”. A group of types that satisfy a number of operations. There is, for example the Show type class that has only one operation: show. That’s what print uses to convert - anything that can be converted to a string - to a string.

There is something else that is very helpful to us: Integral. That’s a type class that groups everything that can be divided with an error, and that’s also where we got our quotRem from.

(By the way: There is a type-class called Num that provides basic arithmetic logic, that is +, -, * and negation.)

For making our example work with Integrals we only need to change our type-signature, not our code:

convert :: Integral i => i -> i -> [i]

So when we call the function with an Int, then it fills it into the type signature:

convert 2 42
-- here the type is now:
convert :: Integral Int => Int -> Int -> [Int]
-- type checker asks: Is "Integral Int" true? Yes.
--  there exists a type class Integral for the type Int.
-- so the result is:
convert :: Int -> Int -> [Int]

So what’s the “i” for?

It requires that all the types in there are the same, and what type class should exist for the types that are going to be put into those slots.

Type classes are a wonderful thing: They allow us to group data types by what you can do with them. Instead of asking: What data do I need? I ask: What does my data need to be able to do? It’s usage-oriented, and that’s a really nice property.

Also, it’s generalizing and that’s always nice for programmers to see ;)

Side Note

I didn’t say a word on this blog for a long time. And this blog post turned out to become pretty big… Well, it’s okay I guess… At least you seem to have read through this wall ;)

This wasn’t meant to be a tutorial in the beginning. I just wanted to make everything clear that couldn’t be clear, but only did that for some things. In the end it turned out to be a little messy, too. I think this is most helpful for people who wrote other programming languages before, so it’s maybe not so good for newcomers. For those I suggest: read through this post, try to remember what you understood and try out some other tutorials as well :)

21st March 2014

Photo with 1 note

Interactive Seperating Axis Theorem Visualization

Just take a look at this:

https://www.desmos.com/calculator/xagrux7ssl

It took quite some time to write (~160 equations), because you don’t have things like vectors on Desmos.com, but it was really nice to play around on this editor and finding out how to do things.

I hope the tutorial makes sense and helps understanding how SAT works, but personally I think the best thing with this is the ability to interact with it :)

Interactive Seperating Axis Theorem Visualization

Just take a look at this:

https://www.desmos.com/calculator/xagrux7ssl

It took quite some time to write (~160 equations), because you don’t have things like vectors on Desmos.com, but it was really nice to play around on this editor and finding out how to do things.

I hope the tutorial makes sense and helps understanding how SAT works, but personally I think the best thing with this is the ability to interact with it :)

18th January 2014

Post with 2 notes

Sharing Links

So, just a pretty cool video I’d like to share with you from the beginning ;) http://vimeo.com/79098420 (It’s about simulating bipedal creatures realistically with muscles. These creatures learn walking with a neuronal system and without any motion captures)

Bret Victor (worrydream.com)

You really have to check out Bret Victor’s Website. He has done so much awesome research!

Ladder of Abstraction & Learnable Programming

Look at his essays the ladder of abstraction or learnable programming to get an idea of what he is doing, and how he is trying to revolutionize UI’s and PC User interaction.

Inventing on Principle

I also highly recommend his talks, especially the talk “Inventing on Principle”, which is about how game editors should look like (or better: How IDE’s should look like in general), in terms of helping the user understand what is going on, when writing code, building up the connection between glyphs and letters and the graphical stuff they magically create.

Drawing Dynamic Visualizations

Also recommended is “Drawing Dynamic Visualizations”, which is about a tool that helps abstracting away the input of data when drawing graphs. Basically, when you want to create a diagramm, you have 3 options:

  • Adobe Illustrator: It’s possible to use it for drawing graphs, that can be very outstanding, but they only work for one data input.
  • Excel: Using Excel or similar is also not an option, because you can have dynamic input on the one hand, but can’t have outstanding, ‘different’ graphs on the other hand (that means: Only bar charts, pie charts and other common stuff). You can’t visualize data in a way, that might be very specific to the type of data you want to visualize.
  • Writing code: The third option would be writing code (using d3, for example), but that’s not much of an option, because when writing code you need to be a programmer. You need to go through complicated vector math stuff (sometimes), you need to go through the API docs of the library you use. And if you finally wrote all that code to create your very special chart that works with different input sets of the same type, you’ve spent a lot of time writing that code, and while writing you were blind.

I really recommend all of the talks Bret Victor gave, but these are my Top 2. He has inspired many people to create cool stuff, for example:

Light Table

Have you seen this already? It’s a really good idea, and the creator said he was inspired by one of Bret Victor’s talks.

LightTable’s website

(If you want to take a look on what the idea is and how it looks, see the demonstration video)

About me

I haven’t wrote a Blog Post for a long time now… But I’ve been programming a lot recently. I don’t know how up-to-date you are, but I’ve been learning and programming a lot of haskell recently (It’s a purely-functional programming language).

Also, I now have “computer science” lessons at school (it’s called “Informatik Kurs” in germany…), which means I’m now also programming in school, not only at home ;). Basically we’ve learned about websites and webservers and html and php. After half a year of those lessons, we (the guys going to those lessons) were supposed to got together in little groups / teams, who develop a simple WWW solution for a problem. Our idea was a website where you could register and upload files, that are automatically encrypted (client side). You could specify what other accounts you want to share your file with or specify a group of accounts. If a file was sent to you, then you can download the file and decrypt it (on the client side), if the other user gave you the key for decrypting.

You can see our (we’re a team of 4 students) progress on our github repository (beware, it’s german ;) ).

It was already a really nice experience since we started writing. In the beginning I said I wanted to do synchronization between us using git and github. That was new to the others and a challenge for me, because we are also programming at school, and at school we are trapped inside the intra-net of the school together with a couple of entry points to the internet. That means we couldn’t directly push our code to github, but we found a solution, which works very well (I won’t describe our solution here, though).

Other Webserver Technologies

And since, after writing ~2000 lines of php code, I got really tired of a really badly designed language (see php, a fractal of bad design), I wanted to try out some alternatives :)

NodeJs

I’ve tried out NodeJs, but it feld kind of much more lower-level that what I was used to before. I should have - maybe - used Jade, but I’ve heard of it just after writing my test project

But all in all I felt it was much nicer being in a language like Javascript, but the weak typing was still bugging me, sooo…

Happstack (haskell)

…I tried out Happstack (see especially the page “why”). It’s written in haskell and you use it by writing haskell. Basically it’s a webserver library written in haskell.

It felt muuuuch nicer to work with it.

The biggest thing I hated, was that documentation is rare. Blog posts with examples aren’t a common thing, when it comes to haskell. Finding examples for happstack coding was not the problem. Happstack has kind of it’s own philosophy of how you need to write your code, and they don’t seem to think that SQL is a good solution for saving data. Therefore they created happstack-state, which was recently deprecated in favour of acid-state. Now the problem is, that even though a couple of blog post examples exist for happstack-state, almost none exist for acid-state, and finding example code was not easy …

But well, I got it working! :) Again, see my Test Project, written using (only) haskell, happstack-lite and acid-state.

What I really liked both about happstack and node.js, was that ‘setting up’ a webserver was muuuuch easier. In haskell you’d do:

runhaskell Main.hs (where Main.hs is your file with the Main module, starting the webserver, simply by calling serve serverConfig webpages)

And in node.js it’d be pretty similar:

node server.js

Both starts up a server at a port, given in code. I had to juggle around with 3 to 4 different config files when using lampp and not everything was working in the end (phpMyAdmin doesn’t work for me anymore :/ ), even though I only wanted to move the htdocs directory into my home directory…

If you’d want to move your webserver files on your server, you’d simply copy your directory to somewhere else, cd there and start the server with node / runhaskell.

All in all, I’ve had a lot of fun in 2013 and am having a lot of fun in 2014 currently, too :) (Also, the minecraftmonkeys (beware, it’s german again :P ) have started making youtube videos, too, which makes me really happy)

(I am sorry for this long, and not-well-structured and not-having-a-specific-topic blog post…)

15th January 2014

Link with 1 note

A Worst Case for Functional Programming? →

3rd January 2014

Question

gef4k said: Hi Matheus ! Thanks for comments and reblogging. I will post explanations on how rendering works, I also can give the sourcecode, but my 4k sourcecode is organized for final compression, so there are fews illogical stuffs in it !

Very cool! :)

I can’t wait to see how it works, your game is very inspiring and impressive!

25th December 2013

Video reblogged from Gef4K with 6 notes

gef4k:

Just to see it in action : In The Dark 4K - First level - Gameplay

Gef4K.

Wow. Amazing voxel effect!

Have you released the source code / plan to do so? Are you maybe planning to create a library that allows rendering such things? Especially the lighting / raycasting is interesting to me. Would be cool to see something like that in OpenGL, too :)

Keep up that awesome work! :)

2nd December 2013

Post

Crazy Haskell Type Signature!

pSwitch :: Functor col
        => (forall sf. (in -> col sf -> col (ext, sf)))
        -> col (SF ext out)
        -> SF (in, col out) (Event mng)
        -> (col (SF ext out) -> mng -> SF in (col out))
        -> SF in (col out)

From: FRP.Yampa.pSwitch

27th September 2013

Link

Are buffer-overflows solved yet? A historical tale. →

5th September 2013

Post with 2 notes

Scala Units Of Measure with Value Classes

Today I’m going to talk a little about Value Classes in scala. The SIP was accepted, you can see it here: http://docs.scala-lang.org/sips/pending/value-classes.html

It’s very useful since it allows unboxed units of measure and therefore type-checking your units while still running fast.

But fist, I’m going to explain one of the most relevant use cases to me, as a game developer.

The Viewport

Let’s assume you’re writing a game. In most cases today, you will have a world that is actually larger than what can be displayed on the user’s/player’s screen. So what you’re going to do is have a camera that pans around in the game world, and as soon as the player walks other parts of the actual game world will be viewed. That’s what most people call a Viewport (not talking about the gl viewport!). You can imagine a Viewport to be kind of a camera that views only a portion of the actual world.

A Viewport basically only stores the panning values (the x and y offset from the world origin) and, when rendering, moves everything to the right place. So when you have a character placed at position (100, 100) in the game world and your Viewport is offset at (20, 20), then the character is going to appear at (80, 80) on the screen.

Coordinate Spaces

So what we have now is two so called ‘spaces’ in which numbers occur. We have the ‘World space’-coordinates and the ‘Screen space’-coordinates.

The only problem that usually occurs is that when you sometimes directly supply the World-Space coordinates to the renderer, so your entity doesn’t get rendered properly. There is nobody and nothing that warns you from doing that. And you probably already wondered “What has that now to do with our value classes!?”, but that’s, finally what we use our value class for.

Using Value Classes for solving problems

(And reduce error likeliness)

What we do is, we create a value class for the type Float. You mark a normal class as a value class by extending AnyVal. You’ll see what effect that has in a moment:

class PixelsWorld(val u: Float) extends AnyVal
class PixelsScreen(val u: Float) extends AnyVal

Now that we have those, let’s define some game stuff that uses those classes:

class Entity(var x: PixelsWorld, var y: PixelsWorld)

// You need that layer of abstraction. It doesn't change
// anything, it just forces the "PixelsScreen" type
def draw(x: PixelsScreen, y: PixelsScreen) {
    drawActualImplementation(x.u, y.u);
}

def drawActualImplementation(x: Float, y: Float) = 
    println("Drawing at (" + x + ", " + y + ")")

And when we now try to call draw() with the wrong type, that means using PixelsWorld instead of PixelsScreen, the compiler will give us an error:

// You can easily feed it Float's and it'll accept them as PixelsWorld:
val entity = new Entity(10f, 10f)

// There doesn't seem to be anything wrong with this
// on the first glance, right?
draw(entity.x, entity.y)
:38: error: type mismatch;
 found   : PixelsWorld
 required: PixelsScreen
              draw(entity.x, entity.y)
                          ^

Nice!

Whenever we try to do dumb stuff, we actually get warned! We can’t compile then.

What we now have to do is convert our PixelsWorld into PixelsScreen somehow… That’s where our Viewport comes into play. We’ll define a method called ‘convert’ in the Viewport, that produces the right PixelsScreen positions when we give it the PixelsWorld position.

// The viewport itself has a position in the world:
class Viewport(var x: PixelsWorld, var y: PixelsWorld) {
  // (x, y) => (x, y)
  def convert(x: PixelsWorld, y: PixelsWorld): (PixelsScreen, PixelsScreen) =
    (new PixelsScreen(x.u-this.x.u), new PixelsScreen(y.u-this.y.u))
}

One little thing I’d like to add is an implicit value class (explaining it would be out of scope, though), which let’s us define the space with less code:

implicit class PixelsWorldFloat(val f: Float) extends AnyVal {
  // creates a PixelsWorld instance, 
  // by simply calling this method on floats:
  def pxWorld = new PixelsWorld(f)
}

val myPxWorld: PixelsWorld = 10f.pxWorld

(The exact same pattern applies to PixelsScreen)

This class, due to value classes, has no runtime overhead at all, too.

Now we have our complete, type-checking, unit-checking code:

val entity = new Entity(100f.pxWorld, 100f.pxWorld)
val view = new Viewport(20f.pxWorld, 20f.pxWorld)

val (drawx, drawy) = view.convert(entity.x, entity.y)
draw(drawx, drawy)

Other uses

Box2D Units

You have probably already heard, that Box2D doesn’t represent Body positions in pixels, but in meters. And usually you don’t want 1 pixel to be 1 meter, so you have to have some kind of conversion method there too. With units you could create the MetersWorld, the PixelsWorld and the PixelsScreen with conversion methods between all of those.

LibGDX Camera

The way I have set this system up in my game code that uses LibGDX’s OthogonalCamera is like this:

class Viewport(x: PixelsWorld, y: PixelsWorld, screenSize: ListenableProperty[Size]) {

  private val cam = new OrthographicCamera()
  val size = screenSize()
  cam.viewportWidth = size.width
  cam.viewportHeight = size.height
  cam.setToOrtho(true)

  def convert(x: PixelsWorld, y: PixelsWorld): (PixelsScreen, PixelsScreen) = {
    val vec3 = new Vector3(x.u, y.u, 0)
    cam.project(vec3)
    (vec3.x.pxScreen, vec3.y.pxScreen)
  }

  def convert(x: PixelsScreen, y: PixelsScreen): (PixelsWorld, PixelsWorld) = {
    val vec3 = new Vector3(x.u, y.u, 0)
    cam.unproject(vec3)
    (vec3.x.pxWorld, vec3.y.pxWorld)
  }

  // ...

}

Pseudo-Physics-Units

You could create Units like Length, Time, Mass and then create more complex Units out of those: Area(Length, Length), Volume(Length, Length) or even more advanced like Newtons(Mass, Length, Time).

Though those might not be as ‘cool’ as the Measure type system in F#, where it would automatically know the type Length * Length * Length, without you creating a new Unit specifically for that usage.

Read more

SIP 15 - Value Classes

Scala-lang.org Value Class Introduction

Another approach - macros:

Units of Measure - scalamacros.org

Tagged: scalaprogrammingunits of measurementgame programming

2nd September 2013

Post

All ways for foreach

Here are all syntactic ways of making a valid for-each in scala.

They all work.

val list = "abcdefghi".split("")

for (i <- list) {
  Console.print(i)
}

list.foreach { i =>
  Console.print(i)
}

list.foreach((i) => {
  Console.print(i)
})

list.foreach((i) => Console.print(i))

list.foreach(Console.print(_))

I think it might even be very helpful to anyone learning scala, so they understand all that new syntax in scala (in comparison to java).

In the end I think every way of writing it has a specific purpose (I use every version except for the 3rd and 4th) and they make writing scala much easier.

You can put it straight into the repl to try it out :)

EDIT: This is also possible:

list.foreach(Console.print)

Tagged: scalaprogrammingloopscode