Arrays and Specialized Arrays in Kotlin
1. Introduction
Arrays are one of the most fundamental data structures in programming, allowing
you to store and manipulate collections of elements. Kotlin provides a powerful
and concise implementation of arrays, blending traditional array concepts with
modern language features. Whether you’re working with fixed-size collections or
need specialized types for performance, Kotlin’s array support has you covered.
In this post, we’ll explore Kotlin arrays and their specialized variants,
examining their features, syntax, and best practices for effective usage.
2. Overview of Arrays
An array in Kotlin
looks like this:
val array = arrayOf(10, 20, 30, 40, 50)
println(array[0]) // Accesses 10
println(array[3]) // Accesses 40
which can be visualized as:
+-----+-----+-----+-----+-----+
| 0 | 1 | 2 | 3 | 4 | <- Index
+-----+-----+-----+-----+-----+
| 10 | 20 | 30 | 40 | 50 | <- Values
+-----+-----+-----+-----+-----+
Definition and Purpose
An array in Kotlin is a collection of elements of the same type, stored in a
contiguous block of memory. Arrays are particularly useful for scenarios
requiring:
- Fixed-size collections.
- Fast access to elements by index.
- Compact storage of homogeneous data.
Key Characteristics
- Fixed Size: Once created, the size of an array cannot be changed.
- Index-based Access: Elements can be accessed using zero-based indices.
- Mutable: Array elements can be updated.
3. Kotlin Implementations
General Array
The Array
class in Kotlin can hold elements of any type. It is generic,
allowing arrays of primitive or non-primitive types.
Syntax for Creating an Array
- Using
arrayOf()
:
val fruits = arrayOf("Apple", "Banana", "Cherry")
// creates an array of strings
val nums = arrayOf(1, 2, 3, 4, 5)
// creates an array of integers
- Using a Constructor:
val squares = Array(5) { it * it }
// creates an array of integers: [0, 1, 4, 9, 16]
Specialized Arrays
For better performance, Kotlin provides specialized arrays for primitive types:
IntArray
for integers.DoubleArray
for doubles.CharArray
for characters.- Other types:
ByteArray
,ShortArray
,LongArray
,BooleanArray
.
Syntax for Creating Specialized Arrays
- Using
intArrayOf()
:
val numbers = intArrayOf(1, 2, 3, 4, 5)
// creates an array of integers
- Using a Constructor:
val evens = IntArray(5) { it * 2 }
// creates an array of integers: [0, 2, 4, 6, 8]
4. How to Use Arrays
Accessing Elements
You can access elements using indices:
val fruits = arrayOf("Apple", "Banana", "Cherry")
// array of strings
val firstFruit = fruits[0]
// Accessing the first element (Apple)
Here using Kotlin Playground you can test this code-
Updating Elements
val fruits = arrayOf("Apple", "Banana", "Cherry")
// array of strings
fruits[1] = "Blueberry"
// Updating the second element (from Banana to Blueberry)
Here using Kotlin Playground you can test this code-
Iterating Over an Array
- Using
for
Loop:
val fruits = arrayOf("Apple", "Banana", "Cherry", "Date", "Mango")
// array of strings
for (fruit in fruits) {
println(fruit)
// prints each fruit on a new line
}
Here using Kotlin Playground you can test this code-
- Using
forEach
Function:
val fruits = arrayOf("Apple", "Banana", "Cherry", "Date", "Mango")
// array of strings
fruits.forEach { println(it) }
// prints each fruit on a new line
Here using Kotlin Playground you can test this code-
Common Operations
- Finding Size:
val fruits = arrayOf("Apple", "Banana", "Cherry", "Date", "Mango")
// array of strings
println(fruits.size)
// Output: 5
- Sorting:
val fruits = arrayOf("Apple", "Cherry", "Banana", "Avocado", "Date", "Mango")
val sortedFruits = fruits.sortedArray()
// sorts the array alphabetically : [Apple, Avocado, Banana, Cherry, Date, Mango]
- Checking for Element:
val fruits = arrayOf("Apple", "Cherry", "Banana", "Avocado", "Date", "Mango")
println("Banana" in fruits)
// Output: true
5. Array Extensions in Kotlin
Kotlin provides several extension functions for arrays that make working with
them much easier. Below are some of the most useful:
sum()
: Returns the sum of numeric elements.
val arr = arrayOf(1, 2, 3, 4, 5)
println(arr.sum()) // Output: 15
shuffled()
: Returns a new array with elements shuffled.
val shuffledArr = arr.shuffled()
println(shuffledArr.joinToString())
filter()
: Filters elements based on a predicate.
val evenNumbers = arr.filter { it % 2 == 0 }
println(evenNumbers.joinToString()) // Output: 2, 4
map()
: Applies a transformation to each element.
val squared = arr.map { it * it }
println(squared.joinToString()) // Output: 1, 4, 9, 16, 25
sorted()
: Returns a sorted array.
val sortedArr = arr.sortedArray()
println(sortedArr.joinToString())
take()
: Returns the firstn
elements.
val firstThree = arr.take(3)
println(firstThree.joinToString()) // Output: 1, 2, 3
drop()
: Returns all elements except the firstn
.
val withoutFirstTwo = arr.drop(2)
println(withoutFirstTwo.joinToString()) // Output: 3, 4, 5
distinct()
: Returns an array with duplicate elements removed.
val withDuplicates = arrayOf(1, 2, 2, 3, 3, 3)
val distinctArr = withDuplicates.distinct()
println(distinctArr.joinToString()) // Output: 1, 2, 3
- **
contains()
**: Checks if an element is present in the array.
val hasThree = arr.contains(3)
println(hasThree) // Output: true
indexOf()
: Returns the index of the first occurrence of an element.
val index = arr.indexOf(3)
println(index) // Output: 2
lastIndexOf()
: Returns the index of the last occurrence of an element.
val lastIndex = arr.lastIndexOf(3)
println(lastIndex) // Output: 2
count()
: Returns the number of elements satisfying a condition.
val count = arr.count { it % 2 == 0 }
println(count) // Output: 2
any()
: Checks if any element satisfies a condition.
val hasEven = arr.any { it % 2 == 0 }
println(hasEven) // Output: true
all()
: Checks if all elements satisfy a condition.
val allEven = arr.all { it % 2 == 0 }
println(allEven) // Output: false
6. Specialized or Variant Types
Specialized Arrays
Specialized arrays in Kotlin are designed for primitive types, offering enhanced performance and
memory efficiency compared to generic arrays. Below are some specialized array types available in
Kotlin:
1. IntArray
- Primitive Type: Integer numbers
- Description: An array for storing integers.
- Example Syntax:
val numbers = intArrayOf(1, 2, 3)
- Example Values:
[1, 2, 3]
2. DoubleArray
- Primitive Type: Double-precision floating point
- Description: An array designed for storing
Double
values. - Example Syntax:
val decimals = doubleArrayOf(1.1, 2.2)
- Example Values:
[1.1, 2.2, 3.3]
3. FloatArray
- Primitive Type: Single-precision floating point
- Description: An array for storing
Float
values. - Example Syntax:
val floats = FloatArray(3) { it * 1.0f }
- Example Values:
[0.0, 1.0, 2.0]
4. CharArray
- Primitive Type: Characters
- Description: An array used for storing
Char
values. - Example Syntax:
val letters = charArrayOf('a', 'b', 'c')
- Example Values:
['a', 'b', 'c']
5. BooleanArray
- Primitive Type: Boolean values
- Description: An array for storing
Boolean
values. - Example Syntax:
val flags = booleanArrayOf(true, false)
- Example Values:
[true, false]
6. ByteArray
- Primitive Type: 8-bit integer
- Description: An array for storing
Byte
values. - Example Syntax:
val bytes = byteArrayOf(1, 2, 3)
- Example Values:
[1, 2, 3]
7. ShortArray
- Primitive Type: 16-bit integer
- Description: An array designed to store
Short
values. - Example Syntax:
val shorts = shortArrayOf(1000, 2000)
- Example Values:
[1000, 2000]
8. LongArray
- Primitive Type: 64-bit integer
- Description: An array that stores
Long
values. - Example Syntax:
val longs = longArrayOf(100000L, 200000L)
- Example Values:
[100000, 200000]
When to Use Each Type
- Array should be used for mixed or non-primitive types.
- Specialized arrays like
IntArray
,DoubleArray
, etc., are ideal for performance-critical tasks
involving primitive types.
7. Performance and Best Practices
When to Use Arrays
- For fixed-size collections requiring fast, index-based access.
- When performance is critical and specialized arrays can be leveraged.
Best Practices
- Use the Right Type: Prefer specialized arrays for primitives to avoid
unnecessary boxing. - Use Kotlin Extension Functions: Leverage Kotlin’s rich set of array
functions (map
,filter
, etc.) for cleaner code. - Immutable Collections: For dynamic collections, consider using
List
instead ofArray
for better flexibility and safety.
8. Code Examples
Example 1: General Array
Example 2: Specialized Array - Mathematical Operations
Example 3: Real-World Use Case - Tracking Sales Over a Week
Example 4: Using Array Extensions - Filtering and Transformation
Example 5: Object Array - Working with Data Classes
Example 6: Advanced Specialized Array - Working with BooleanArray
Example 7: Advanced Real-World Use Case - Student Scores Analysis
9. Similar Data Structures
- List vs Array: Use
List
for dynamic sizing;Array
for fixed size. - MutableList vs Array:
MutableList
provides more flexibility for
adding/removing elements dynamically.
10. Conclusion
Arrays in Kotlin are versatile and efficient for handling fixed-size
collections. Whether you’re working with general arrays or specialized variants,
Kotlin’s syntax and extension functions make them easy to use. By understanding
their strengths and trade-offs, you can make informed decisions about when and
how to use arrays in your applications.
Experiment with arrays in Kotlin and see how they can streamline your
programming tasks!