Documentation Index
Fetch the complete documentation index at: https://soul-lang.com/llms.txt
Use this file to discover all available pages before exploring further.
index
Index access allows you to retrieve and modify elements in arrays, lists, strings, and object properties using square bracket notation []. This is fundamental for working with collections and data structures in Soul.
Array Index Access
Access array elements by their numeric index:
numbers = [10, 20, 30, 40, 50]
// Read elements
first = numbers[0] // 10
second = numbers[1] // 20
last = numbers[4] // 50
// Modify elements
numbers[0] = 100 // [100, 20, 30, 40, 50]
numbers[2] = 300 // [100, 20, 300, 40, 50]
Negative Index Access
Access elements from the end of arrays:
items = ["apple", "banana", "cherry", "date"]
// Negative indices (if supported)
last = items[-1] // "date"
secondLast = items[-2] // "cherry"
// Alternative: calculate from length
last = items[items.length() - 1] // "date"
secondLast = items[items.length() - 2] // "cherry"
String Index Access
Access individual characters in strings:
text = "Hello"
// Read characters
first = text[0] // "H"
second = text[1] // "e"
last = text[4] // "o"
// Note: String modification may not be supported
// text[0] = "h" // May not work - strings might be immutable
Object Property Index Access
Access object properties using string keys:
user = {
"name": "Alice",
"age": 30,
"email": "alice@example.com"
}
// Read properties
name = user["name"] // "Alice"
age = user["age"] // 30
// Modify properties
user["age"] = 31
user["city"] = "New York"
Dynamic Index Access
Use variables as indices:
data = [100, 200, 300, 400, 500]
key = "name"
user = {"name": "Bob", "age": 25}
// Dynamic array index
index = 2
value = data[index] // 300
// Dynamic object property
property = user[key] // "Bob"
// Using expressions as indices
middle = data[data.length() / 2]
Multi-dimensional Arrays
Access nested arrays:
matrix = [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9]
]
// Access nested elements
element = matrix[1][2] // 6 (row 1, column 2)
row = matrix[0] // [1, 2, 3]
// Modify nested elements
matrix[2][1] = 80 // Changes 8 to 80
Nested Object Access
Access nested object properties:
user = {
"profile": {
"name": "Alice",
"address": {
"street": "123 Main St",
"city": "New York"
}
}
}
// Access nested properties
name = user["profile"]["name"] // "Alice"
city = user["profile"]["address"]["city"] // "New York"
// Modify nested properties
user["profile"]["address"]["city"] = "Boston"
Array of Objects Index Access
Access properties of objects in arrays:
users = [
{"name": "Alice", "age": 25},
{"name": "Bob", "age": 30},
{"name": "Charlie", "age": 35}
]
// Access object properties in array
firstUserName = users[0]["name"] // "Alice"
secondUserAge = users[1]["age"] // 30
// Modify object properties in array
users[0]["age"] = 26
users[2]["name"] = "Charles"
Index with Expressions
Use complex expressions as indices:
data = [10, 20, 30, 40, 50]
// Arithmetic expressions
middle = data[data.length() / 2]
next = data[currentIndex + 1]
// Function calls as indices
index = findIndex(data, target)
value = data[index]
// Conditional expressions
selectedIndex = isEven ? 0 : 1
selectedValue = data[selectedIndex]
Safe Index Access
Handle index bounds safely:
soul safeGet(array, index) {
if (index >= 0 && index < array.length()) {
return array[index]
}
return null
}
soul safeSet(array, index, value) {
if (index >= 0 && index < array.length()) {
array[index] = value
return true
}
return false
}
// Usage
numbers = [1, 2, 3, 4, 5]
value = safeGet(numbers, 10) // null (safe)
success = safeSet(numbers, 2, 100) // true
Index in Loops
Use indices in loop constructs:
items = ["apple", "banana", "cherry"]
// Traditional for loop with index
for (i = 0; i < items.length(); i++) {
println("Index " + i + ": " + items[i])
}
// For-in loop with index (if supported)
for (index, item in items) {
println("Index " + index + ": " + item)
}
Index Assignment Patterns
Different ways to assign values using indices:
// Direct assignment
arr[0] = "new value"
// Conditional assignment
if (arr[index] == null) {
arr[index] = "default"
}
// Assignment with computation
arr[i] = arr[i] + 10
// Assignment from other arrays
arr1[i] = arr2[j]
Index with Error Handling
Handle index access errors:
soul getElement(array, index) {
try {
return array[index]
} catch (error) {
println("Index access error: " + error)
return null
}
}
soul setElement(array, index, value) {
try {
array[index] = value
return true
} catch (error) {
println("Index assignment error: " + error)
return false
}
}
Index with Object Methods
Use index access with object methods:
data = {
"items": [1, 2, 3, 4, 5],
"config": {"debug": true}
}
// Method-like access
firstItem = data["items"][0]
debugMode = data["config"]["debug"]
// Combined with method calls
length = data["items"].length()
uppercased = data["items"][0].toString().toUpperCase()
Optimize index access:
// Cache array length
items = getItems()
length = items.length()
for (i = 0; i < length; i++) {
processItem(items[i])
}
// Cache frequently accessed objects
config = getConfig()
debugMode = config["debug"]
logLevel = config["logLevel"]
Index Validation
Validate indices before use:
soul validateIndex(array, index) {
if (array == null) {
return false
}
if (typeof index != "number") {
return false
}
return index >= 0 && index < array.length()
}
soul accessWithValidation(array, index) {
if (validateIndex(array, index)) {
return array[index]
}
throw("Invalid index: " + index)
}
Best Practices
- Check bounds: Always validate indices before use
- Use meaningful names:
users[currentIndex] instead of users[i]
- Handle errors: Wrap index access in try-catch when needed
- Cache lengths: Store array lengths in variables for performance
- Use safe access: Create helper functions for safe index operations
// Good - safe index access
soul getUserById(users, userId) {
for (i = 0; i < users.length(); i++) {
if (users[i]["id"] == userId) {
return users[i]
}
}
return null
}
// Better - with validation
soul getUserById(users, userId) {
if (users == null || users.length() == 0) {
return null
}
for (i = 0; i < users.length(); i++) {
user = users[i]
if (user != null && user["id"] == userId) {
return user
}
}
return null
}
Index access is fundamental to working with data structures in Soul. Use it carefully with proper bounds checking and error handling to create robust applications.