PK - Chapter 4 Flashcards

1
Q
# *_Define a function_* "foo" with an Int parameter
and an Int return of the parameter squared.
A

fun foo(pInt: Int) = pInt * pInt

  • the Int return value is inferred by the compiler
  • can only be inferred for a single expression
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
2
Q
# Define a function "foo" with a String parameter
and a String return of the parameter contatenated
with "Hello World".
A

fun foo(pString: String) = “${pString} and Hello World”

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
3
Q

What is a single expression function ?

A
  • Only has a single expression
  • does not need braces
  • does not need to specify the return type
  • uses the “=” sign rather than the “return” keyword
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
4
Q

Describe member functions.

A
  • defined inside a class, object or interface
  • invoked using the name of the containing class,
    or object, with a dot notation
  • member functions can reference other functions
    in the object or class, with no additional syntax
  • member functions can access and modify member
    variables of the class
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
5
Q

What is the DRY principle ?

A

Don’t Repeat Yourself

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
6
Q

Describe Local Functions.

A
  • also called nested functions
  • declared inside other functions
  • can be nested several times
  • not accessible to code outside the containing function
  • can access parameters and variables in the outer scope
  • does not need to define the parameters or variables in the outer scope
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
7
Q

Use local functions inside a for loop
and when clause.

A
fun fizzBuzz(start: Int, end: Int) {
 for (k in start..end) {
 fun isFizz() = k % 3 == 0
 fun isBuzz() = k % 5 == 0
 when (
 isFizz() && isBuzz() -\> println("Fizz Buzz")
 isFizz() -\> println("Fizz")
 isBuzz() -\> println("Buzz")
 }
 }
}
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
8
Q

Explain top-level functions.

A
  • defined outside any class, object or interface
  • used to create standalone functions that do
    not belong to any object
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
9
Q

What are the 4 types of functions ?

A
  • member functions
  • extension functions (special case of member function)
  • local functions
  • top-level functions
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
10
Q

Explain named parameters.

A
  • when calling a function, the parameters can be named
  • explicit naming makes the intent clear
  • minimizes errors
  • not all parameters need to be names
  • once a parameter has been named, all subsequent
    parameters in the signature must be named
  • named parameters allow the order of parameters to
    be changed
  • cannot be used on Java-defined functions
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
11
Q

Explain default parameters.

A
  • can be used to define functions and constructors
  • specified in the signature with the “=” sign
  • can omit parameters with a default
  • once a parameter is omitted, all subsequent
    parameters must be omitted, unless the
    parameters are named
  • default parameters, used with named parameters,
    is very powerful and eliminates bolierplate code
    for overrides
  • when overriding a function with default parameters,
    we must keep the same function signature
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
12
Q

Explain extension functions.

A
  • enables you to create a new method on a class,
    without extending or wrapping it
  • you cannot override a function in the underlying class
    that has the same signature (name, parameters,
    order, return)
  • when defined as a top-level function in another file,
    it must be imported
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
13
Q

Why create an extension function ?

A
* frequently used to add a function to a final class,
 or a class in an SDK that you do not want to extend
* avoids creating subclasses, or wrappers, which
 would require code changes to use the new class
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
14
Q
# Define extension function "bar{}"
for class "Foo".
A

fun Foo.bar() = “Foo Bar !”

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
15
Q

Explain extension function precedence.

A

Extension function are resolved in the following order:

  • look for the method signature in the current receiver
  • look in the superclass(es)
  • look at the extension imports that are in scope
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
16
Q

Create an extension function that handles nulls.

A

fun Any?.safeEquals(other: Any?): Boolean {
if (this == null && other == null) return true
if (this == null return false
return this.equals(other)
}

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
17
Q

What is a member extension function ?

A

Extension functions are usually declared at the top level.

A member extension function is defined inside a class.
Its scope is limited and no import is required.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
18
Q

Give an example of a mapping receiver
versus an extension receiver.

A
Extension receiver is an object of the class on
which the extension was defined and called.

A method in a class is called the dispatch receiver.

When there is shadowing of names, the extension receiver
will take precedence, so you must qualify the dispatch receiver.

private fun String.stringAdd() {
map.put(this@ContainerClass.hashCode(), this)
}

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
19
Q

Create a companion object extension.

A

fun Int.Companion.random() : Int {
val random = Random()
return random.nextInt()
}

val int = Int.random()

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
20
Q

Explain the types; Pair and Triple.

A

These contain 2 and 3 identical types, respectively.

An example of Pair…

fun getPair() = Pair(getSomeInt(), getAnotherInt())

val (firstInt, secondInt) = getPair()

val myPair = “London” to “Paris”

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
21
Q

Explain an infix function .

A
  • a function that is placed between 2 operands or arguments,
    so can only operate on 2 arguments
  • first argument is the instance that the function
    is invoked on
  • the second argument is an explicit parameter
    to the function

infix fun concat(other: String) = this + other

val myConcat = “Hello “ concat “World!”

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
22
Q

Explain operator overloading .

A
  • the ability to define functions that use operators
  • operators can only be defined as member functions
    or extension functions
  • can also be referenced with the dot notation and
    english label
  • can act on a different class than they are defined in
  • there is a fixed list of operators that can be used as
    functions, each with an English equivalent name
How well did you know this?
1
Not at all
2
3
4
5
Perfectly
23
Q

What is the list of basic operators
that can be overloaded ?

A

plus
minus
times
div
mod
rangeTo
unaryPlus
unaryMinus
not

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
24
Q

What is the list of advanced operators
that can be overloaded ?

A

contains ( in )
get / set ( [] )
invoke (makes a class look like a function)
compareTo ( <, >, <=, >= )

25
Q

What is the list of assignment operators
that can be overloaded ?

A

These are a more restrictive operators that cannot
be used in conjunction with the basic operators:

plusAssign ( += )
minusAssign ( -= )
timesAssign ( *= )
divAssign ( /= )
modAssign ( %= )

26
Q

Explain functional literals.

A
  • a variable (or val) can contain a function
  • the variable can be called just like a function,
    with the arguments in parenthesis
  • the assignment is made by enclosing the
    code in braces

val printMessage = { message: String -> println(message) }
…or since there is only a single parameter…
val printMessage = { println(it) }

printMessage(“Hello World!”)

27
Q

Explain tail recursive functions.

A

A tail recursive function can be created if:

  • an invocation of a recursive function is the last operation
  • the result is simply to return the call
fun fact(k: Int) : Int {
 tailrec fun factTail(m: Int, n: Int) : Int {
 if (m == 0) return n
 else return factTail(m - 1, m \* n)
 }
 return factTail(k, 1)
}
28
Q

Explain varargs.

A
  • pass a comma-separated list of arguments, which
    is wrapped into an array
  • use the vararg argument before the parameter name
  • can only be one vararg per signature
  • must be the last argument, unless subsequent
    arguments are passed in using named parameters
29
Q

Explain the spread operator.

A

If a function takes a vararg,
and you already have an array,
use the spread operator *

val strings = arrayOf(“a”, “b”, “c”)
doSomething(“First Arg”, *strings)

Future versions of Kotlin will support
collections other than arrays.

30
Q

Name some of the more
common standard library functions.

A
  • apply
  • let
  • with
  • run
  • lazy
  • use
  • repeat
  • require / assert / check
31
Q

What is a closure ?

A

A functional programming concept.

A function that has access to variables and
parameters defined in an outer scope.

It is said that they “close over” the variables
in the outer scope, hence the term closure.

32
Q

Explain Any.apply.

A
  • accepts a lambda
  • the instance that the apply is called on
    is the lambda’s receiver
  • used to create a builder pattern with an object
  • a standard library function, not a method of Any

val task = Runnable { println(“Running!”) }
Thread(task).apply { setDaemon(true) }.start()

33
Q

Describe Any.apply( ?

A
  • Calls the specified lambda with this value
  • *as its receiver and returns this value.**
  • Use it to create a builder pattern with any object.

val task = Runnable { println(“Running”) }
Thread(task).apply { setDaemon(true) }.start()

34
Q

Describe Any.let ?

A
  • Calls the specified closure as its argument
  • *and returns its result.**
  • Creates a temporary variable “it” that can
  • *be used in the closure**
  • Can still access the outer scope with “this”
  • A standard library function, not a method of Any

// need a better example
PrintWriter(“myDocument.txt”).let {
it.append(“$someVariable and some text\n”)
it.close()
}

35
Q

What is the source code for Any.let ?

A
public inline fun T.let(block: (T) -\> R): R {
 contract {
 callsInPlace(block, InvocationKind.EXACTLY\_ONCE)
 }
 return block(this)
}
36
Q

What is the source code for Any.apply ?

A

public inline fun T.apply(block: T.() -> Unit): T {
contract {
callsInPlace(block, InvocationKind.EXACTLY_ONCE)
}
block()
return this
}

37
Q

Describe Any.with(someObject).

A
  • Calls the specified closure with its argument
    as the current receiver
  • Enables you to call multiple functions on an
    object without repeating the receiver each time
  • A standard library function, not a method of Any

val g2: Graphics2D = …
with(g2) {
stroke = BasicStroke(10F)
background = Color.BLACK

}

38
Q

Describe Any.run .

A
  • combines the use cases of with and let
  • a closure is passed to run, which has the instance
    as its current receiver
  • the return value of the closure is the return value of run
  • a standard library function, not a method of Any

val outputPath = Paths.get(“/usr/home”).run {
val path = resolve(“output”)
path.toFile().createNewFile()
path
}

39
Q

Explain “it” versus “this”.

A
  • “this” refers to the current receiver
  • “it” refers to a tighter scope temporary variable
  • used by Any.also and Any.let amoung others
  • used to reference a lambda’s single, unnamed parameter
  • can use “it” in LINQ-style code:

strings.filter { it.length == 5 }.sortedBy { it }.map { it.toUpperCase() }

40
Q

What is a higher-order function ?

A

A function that takes functions as
parameters, or returns a function.

interface Lock { … }
fun <t> lock(lock: Lock, body: () -&gt; T) : T {<br></br> lock.lock()<br></br> try {<br></br> return body()<br></br> }<br></br> finally {<br></br> lock.unlock()<br></br> }<br></br>}</t>

41
Q

Explain the lazy keyword.

A
  • Wraps an expensive function call to be
    invoked once, when first required
  • synchronization is taken care of, eliminating
    race conditions or multiple requests

val lazyString = lazy { readStringFromDatabase() }

42
Q

Explain the use of _underscore “_” in lambdas_.

A

Indicates an unused lambda parameter.

map. forEach { _, value -> println(“$value”) }
map. mapValues { (_, value) -> println(“$value”) }

Note the use of destructuring declaratios syntax
of the Pair in the second example

43
Q

Explain the use keyword.

A

A more concise way of handling closeable
resources in simple cases.

  • an extension on an instance of closeable
  • accepts a function literal that operates on closeable
  • will safely invoke the function, closing down the
    resource afterward; whether or not the function
    completed successfully
val input = Files.newInputStream(Paths.get("input.txt"))
val byte = input.use( { input.read() } )
// the stream will be closed after the read
44
Q

Explain the repeat keyword.

A
  • accepts a function literal and an integer
  • function will be invoked k times

repeat(howMany(), { println(“Hello”) } )

45
Q

What are the
design by contract
keywords ?

A

Used to validate state at runtime

  • require
    assure arguments meet conditions
    throws IllegalArgumentException if not met
  • assert
    assure some logical condition
    throws AssertionException if not met
    can be disabled at runtime
  • check
    assure that internal state meets conditions
    throws IllegalStateException
46
Q

Define a generic function “foo”.

A

fun <t> printRepeat(whatToPrint: T, repeatCount: Int) {<br></br> for (x in 0..repeatCount) {<br></br> println(whatToPrint)<br></br> }<br></br>}</t>

Note that this could have been achieved with:

repeat(repeatCount, { println(whatToPrint) } )

47
Q

Define a pure function.

A
  • deterministic (same output for same input)
  • does not create any side effects

Advantages:

  • can be cached
  • can be parallelized
  • can be tested in isolation
48
Q

How does Kotlin leverage
Single Abstract Methods (SAMs)
implemented in Java.

A
  • SAM is a Java interface that defines a single method
  • there are many of these in the Java standard library
  • Kotlin can convert a function literal into a SAM
val threadPool = Executors.newThreadPool(4)
threadPool.submit { println("Hello World!") }
49
Q

How do you handle keyword conflicts
between Java and Kotlin ?

A

Wrap the conflicting keyword in backticks.

var myDate: Date = …
myDate.when(“2016”)

50
Q

How does Kotlin handle
checked methods in Java ?

A

Kotlin does not have checked exceptions.

Java methods with checked exceptions are
treated the same as methods that do not.

51
Q

How are Java void methods
handled in Kotlin ?

A

Treated as a function
returning Unit.

52
Q

How do you use
top-level functions from Java ?

A
* The functions are defined as Java static methods
 in a class with the name of the package by default
* the *@file:JvmName("MyClassName")* annotation
 will instead create a class named MyClassName
 for top-level functions in this file
* the *@file:JvmMultifileClass("MyClassName")* annotation
 can create a class that is used for all top-level functions
 in the package
@file:JvmName("MyUtils")
package com.company.somepackage
fun cube(n: Int) : Int = n \* n \* n
53
Q

How can Java use a Kotlin
function with default parameters ?

A

Use the @JvmOverloads annotation to
generate all the overloaded methods for Java.

@JvmOverloads fun foo(firstArg: String = “Hello”, secondArg: String = “World”) { }

54
Q

Explain Any.takeIf and Any.takeUnless.

A
  • takeif
    Returns this value if it satisfies the given [predicate] else null
  • takeUnless
    Returns this value if it does NOT satisfy the given [predicate] else null
  • called on the object, so good for chaining
  • standard library functions, not methods on Any

someObject?.takeIf{ booleanPredicate }?.apply { doThis() }

55
Q

Summarize the following
standard library functions:

  • apply
  • also
  • run
  • let
A

Defining attributes:

  • current receiver
  • builder / mapper
56
Q
A
57
Q

What is a
Single Abstract Method (SAM) ?

A
  • an interface that defines a
    single method
  • only for interfaces implemented
    ​in Java
  • SAMs occur frequently in the
    Java standard library
  • you can pass a function literal
    where a SAM is expected
val threadPool = Executors.newFixedThreadPool(4)
threadPool.submit { println("Working hard!") }
58
Q

Create a
named companion object
named “Foo” and call
its methods from Java
and Kotlin.

A
  • often used to create singletons
  • can use @JvmStatic to make the
    someMethod() static
object Foo {
 fun someMethod() { doSomething() }
}
// from Java
Foo.INSTANCE.someMethod()
// from Kotlin
Foo.someMethod()
59
Q

How do you throw an exception
from Kotlin to Java ?

A
  • Java only catches checked exceptions,
    but there are no checked exceptions in
    Kotlin
  • use the @Throws annotation to add the
    exception to the JVM method signature
    for Java
@Throws(IOException::class)
fun createDirectory(file: File) {
 // throw IOException
}