تخطَّ إلى المحتوى

Scala Cheat Sheet

Overview

Scala is a modern multi-paradigm programming language designed to express common programming patterns in a concise, elegant, and type-safe way. It seamlessly integrates features of object-oriented and functional languages, running on the Java Virtual Machine (JVM) with full Java interoperability. Scala’s powerful type system, pattern matching, and immutable data structures make it ideal for building complex, concurrent systems.

Created by Martin Odersky at EPFL in 2003, Scala has become a cornerstone of big data processing (Apache Spark, Kafka, Flink) and distributed systems (Akka). Scala 3 (Dotty) introduced significant improvements including a simplified syntax, union types, opaque types, and an overhauled macro system. The language strikes a balance between academic rigor and practical software engineering.

Installation

# Install Coursier (Scala installer)
curl -fL https://github.com/coursier/coursier/releases/latest/download/cs-x86_64-pc-linux.gz | gzip -d > cs
chmod +x cs && ./cs setup

# macOS
brew install coursier/formulas/coursier && cs setup

# Verify
scala --version
scalac --version
sbt --version

Using SDKMAN

sdk install scala 3.4.0
sdk install sbt 1.9.8

Core Language

Variables and Types

// Immutable (preferred)
val name: String = "Scala"
val age = 42  // Type inference

// Mutable
var counter: Int = 0
counter += 1

// Lazy evaluation
lazy val expensive = computeExpensiveValue()

// Type aliases
type UserId = Long
type Result[A] = Either[String, A]

Basic Types

TypeDescriptionExample
Int32-bit integer42
Long64-bit integer42L
Double64-bit floating point3.14
Float32-bit floating point3.14f
BooleanTrue/falsetrue
CharUnicode character'A'
StringCharacter sequence"hello"
UnitNo value (like void)()
NothingNo instances existBottom type
AnySupertype of everythingTop type

Functions

// Function definition
def add(x: Int, y: Int): Int = x + y

// Default and named parameters
def greet(name: String, greeting: String = "Hello"): String =
  s"$greeting, $name!"

greet("World")                    // "Hello, World!"
greet("World", greeting = "Hi")  // "Hi, World!"

// Anonymous functions
val double = (x: Int) => x * 2
val nums = List(1, 2, 3).map(_ * 2)

// Higher-order functions
def apply(f: Int => Int, x: Int): Int = f(x)
apply(double, 5)  // 10

// Curried functions
def multiply(x: Int)(y: Int): Int = x * y
val triple = multiply(3)(_)
triple(5)  // 15

// By-name parameters (lazy evaluation)
def logIf(condition: Boolean)(message: => String): Unit =
  if (condition) println(message)

Pattern Matching

// Basic matching
val result = x match
  case 0 => "zero"
  case 1 => "one"
  case n if n > 0 => s"positive: $n"
  case _ => "negative"

// Type matching
def process(any: Any): String = any match
  case s: String => s"String: $s"
  case i: Int if i > 0 => s"Positive Int: $i"
  case list: List[_] => s"List of ${list.length}"
  case _ => "Unknown"

// Case class matching
case class User(name: String, age: Int)
user match
  case User("Admin", _) => "admin user"
  case User(name, age) if age >= 18 => s"adult: $name"
  case User(name, _) => s"minor: $name"

// Sealed trait matching (exhaustive)
enum Color:
  case Red, Green, Blue

color match
  case Color.Red => "#FF0000"
  case Color.Green => "#00FF00"
  case Color.Blue => "#0000FF"

Collections

// Immutable collections (default)
val list = List(1, 2, 3)
val set = Set("a", "b", "c")
val map = Map("name" -> "Scala", "version" -> "3")
val vec = Vector(1, 2, 3)  // Efficient random access

// Operations
list.map(_ * 2)               // List(2, 4, 6)
list.filter(_ > 1)            // List(2, 3)
list.foldLeft(0)(_ + _)       // 6
list.flatMap(x => List(x, x)) // List(1, 1, 2, 2, 3, 3)
list.zip(List("a", "b", "c")) // List((1,"a"), (2,"b"), (3,"c"))
list.grouped(2).toList         // List(List(1, 2), List(3))
list.sliding(2).toList         // List(List(1, 2), List(2, 3))
list.forall(_ > 0)             // true
list.exists(_ > 2)             // true

// For comprehensions
val result = for
  x <- 1 to 10
  if x % 2 == 0
  y <- 1 to 3
yield x * y

Object-Oriented Features

// Class
class Animal(val name: String, val sound: String):
  def speak(): String = s"$name says $sound"

// Case class (immutable data holder)
case class Point(x: Double, y: Double):
  def distanceTo(other: Point): Double =
    math.sqrt(math.pow(x - other.x, 2) + math.pow(y - other.y, 2))

// Trait (interface + implementation)
trait Printable:
  def format: String
  def print(): Unit = println(format)

// Enum (Scala 3)
enum Planet(val mass: Double, val radius: Double):
  case Mercury extends Planet(3.303e+23, 2.4397e6)
  case Venus extends Planet(4.869e+24, 6.0518e6)
  case Earth extends Planet(5.976e+24, 6.37814e6)

// Object (singleton)
object Config:
  val maxRetries = 3
  def load(): Config = ???

// Extension methods (Scala 3)
extension (s: String)
  def greet: String = s"Hello, $s!"
"World".greet  // "Hello, World!"

Build Tool (sbt)

Common Commands

CommandDescription
sbt new scala/scala3.g8Create new Scala 3 project
sbt compileCompile project
sbt runRun main class
sbt testRun tests
sbt consoleStart Scala REPL with project
sbt ~compileWatch mode (auto-recompile)
sbt assemblyCreate fat JAR
sbt cleanClean build artifacts

build.sbt

ThisBuild / version := "0.1.0"
ThisBuild / scalaVersion := "3.4.0"

lazy val root = (project in file("."))
  .settings(
    name := "my-project",
    libraryDependencies ++= Seq(
      "org.typelevel" %% "cats-core" % "2.10.0",
      "com.typesafe.akka" %% "akka-actor-typed" % "2.8.5",
      "org.scalatest" %% "scalatest" % "3.2.17" % Test
    )
  )

Configuration

Typesafe Config

// src/main/resources/application.conf
app {
  name = "MyService"
  port = 8080
  database {
    url = "jdbc:postgresql://localhost/mydb"
    pool-size = 10
  }
}
import com.typesafe.config.ConfigFactory

val config = ConfigFactory.load()
val port = config.getInt("app.port")
val dbUrl = config.getString("app.database.url")

Advanced Usage

Given/Using (Scala 3 Implicits)

trait JsonEncoder[A]:
  def encode(value: A): String

given JsonEncoder[Int] with
  def encode(value: Int): String = value.toString

given JsonEncoder[String] with
  def encode(value: String): String = s""""$value""""

def toJson[A](value: A)(using encoder: JsonEncoder[A]): String =
  encoder.encode(value)

toJson(42)       // "42"
toJson("hello")  // "\"hello\""

Futures and Concurrent Programming

import scala.concurrent.{Future, ExecutionContext}
import scala.concurrent.ExecutionContext.Implicits.global

val future = Future {
  Thread.sleep(1000)
  42
}

future.map(_ * 2).foreach(println)

// Combining futures
val combined = for
  a <- Future(computeA())
  b <- Future(computeB())
yield a + b

Troubleshooting

ProblemSolution
ClassNotFoundExceptionCheck classpath; ensure sbt assembly includes deps
Implicit not foundImport givens; check scope and type parameters
Type mismatch errorsUse explicit type annotations to debug inference
Slow compilationUse sbt ~compile for incremental; split into subprojects
Java interop issuesUse @BeanProperty for getters/setters; handle null with Option
Stack overflow in recursionUse @tailrec annotation or trampolining
Binary compatibilityUse %% in sbt for cross-versioned deps
Out of memory in sbtSet SBT_OPTS="-Xmx4G" in environment