0
# List/Array Functions
1
2
Ramda provides 94 comprehensive functions for working with arrays and list-like structures. These functions follow Ramda's core principles of immutability, currying, and function-first data-last parameter order.
3
4
## Core Transformation Functions
5
6
### map
7
Transform each element of a list using a function.
8
9
```javascript { .api }
10
/**
11
* @param {Function} fn - Transformation function (a -> b)
12
* @param {Array} list - List to transform
13
* @returns {Array} New list with transformed elements
14
*/
15
R.map(fn, list)
16
17
// Examples
18
R.map(x => x * 2, [1, 2, 3, 4]); // => [2, 4, 6, 8]
19
R.map(R.toUpper, ['hello', 'world']); // => ['HELLO', 'WORLD']
20
R.map(R.prop('name'), [{name: 'John'}, {name: 'Jane'}]); // => ['John', 'Jane']
21
22
// Curried usage
23
const double = R.map(R.multiply(2));
24
double([1, 2, 3]); // => [2, 4, 6]
25
```
26
27
### filter
28
Select elements that satisfy a predicate function.
29
30
```javascript { .api }
31
/**
32
* @param {Function} predicate - Test function (a -> Boolean)
33
* @param {Array} list - List to filter
34
* @returns {Array} New list with matching elements
35
*/
36
R.filter(predicate, list)
37
38
// Examples
39
R.filter(x => x > 5, [1, 6, 8, 2, 9]); // => [6, 8, 9]
40
R.filter(R.has('active'), [{active: true}, {active: false}, {}]); // => [{active: true}, {active: false}]
41
42
const isEven = x => x % 2 === 0;
43
R.filter(isEven, [1, 2, 3, 4, 5, 6]); // => [2, 4, 6]
44
```
45
46
### reject
47
Remove elements that satisfy a predicate function (opposite of filter).
48
49
```javascript { .api }
50
/**
51
* @param {Function} predicate - Test function (a -> Boolean)
52
* @param {Array} list - List to filter
53
* @returns {Array} New list with non-matching elements
54
*/
55
R.reject(predicate, list)
56
57
// Examples
58
R.reject(x => x > 5, [1, 6, 8, 2, 9]); // => [1, 2]
59
R.reject(R.has('active'), [{active: true}, {active: false}, {}]); // => [{}]
60
61
const isOdd = x => x % 2 === 1;
62
R.reject(isOdd, [1, 2, 3, 4, 5, 6]); // => [2, 4, 6]
63
```
64
65
### reduce
66
Accumulate list elements into a single value.
67
68
```javascript { .api }
69
/**
70
* @param {Function} reducer - Accumulator function ((acc, val) -> acc)
71
* @param {*} initialValue - Starting accumulator value
72
* @param {Array} list - List to reduce
73
* @returns {*} Final accumulated value
74
*/
75
R.reduce(reducer, initialValue, list)
76
77
// Examples
78
R.reduce(R.add, 0, [1, 2, 3, 4]); // => 10
79
R.reduce(R.multiply, 1, [2, 3, 4]); // => 24
80
R.reduce(R.max, -Infinity, [5, 2, 8, 1]); // => 8
81
82
// Building objects
83
const groupBy = (key, list) => R.reduce(
84
(acc, item) => R.assoc(item[key], [...(acc[item[key]] || []), item], acc),
85
{},
86
list
87
);
88
```
89
90
## Search and Selection
91
92
### find
93
Get the first element matching a predicate.
94
95
```javascript { .api }
96
/**
97
* @param {Function} predicate - Test function (a -> Boolean)
98
* @param {Array} list - List to search
99
* @returns {* | undefined} First matching element or undefined
100
*/
101
R.find(predicate, list)
102
103
const users = [{id: 1, name: 'John'}, {id: 2, name: 'Jane'}];
104
R.find(R.propEq(2, 'id'), users); // => {id: 2, name: 'Jane'}
105
R.find(x => x > 10, [1, 5, 15, 3]); // => 15
106
```
107
108
### findIndex
109
Get the index of the first element matching a predicate.
110
111
```javascript { .api }
112
/**
113
* @param {Function} predicate - Test function (a -> Boolean)
114
* @param {Array} list - List to search
115
* @returns {Number} Index of match or -1 if not found
116
*/
117
R.findIndex(predicate, list)
118
119
R.findIndex(R.equals('world'), ['hello', 'world', 'foo']); // => 1
120
R.findIndex(x => x > 100, [10, 50, 150, 200]); // => 2
121
```
122
123
### head, tail, last, init
124
Access list boundaries.
125
126
```javascript { .api }
127
// Get first element
128
R.head(['a', 'b', 'c']); // => 'a'
129
R.head([]); // => undefined
130
131
// Get all but first element
132
R.tail(['a', 'b', 'c']); // => ['b', 'c']
133
R.tail([]); // => []
134
135
// Get last element
136
R.last(['a', 'b', 'c']); // => 'c'
137
R.last([]); // => undefined
138
139
// Get all but last element
140
R.init(['a', 'b', 'c']); // => ['a', 'b']
141
R.init([]); // => []
142
```
143
144
### nth
145
Access element at specific index (supports negative indices).
146
147
```javascript { .api }
148
/**
149
* @param {Number} index - Position to access
150
* @param {Array} list - List to index into
151
* @returns {*} Element at index or undefined
152
*/
153
R.nth(index, list)
154
155
const list = ['a', 'b', 'c', 'd'];
156
R.nth(1, list); // => 'b'
157
R.nth(-1, list); // => 'd' (last element)
158
R.nth(-2, list); // => 'c' (second to last)
159
R.nth(10, list); // => undefined
160
```
161
162
## List Manipulation
163
164
### append, prepend
165
Add elements to list boundaries.
166
167
```javascript { .api }
168
// Add to end
169
R.append('new', ['a', 'b', 'c']); // => ['a', 'b', 'c', 'new']
170
171
// Add to beginning
172
R.prepend('new', ['a', 'b', 'c']); // => ['new', 'a', 'b', 'c']
173
174
// Curried usage
175
const addExclamation = R.append('!');
176
addExclamation(['Hello', 'World']); // => ['Hello', 'World', '!']
177
```
178
179
### insert, insertAll
180
Insert elements at specific positions.
181
182
```javascript { .api }
183
// Insert single element
184
R.insert(2, 'NEW', [1, 2, 3, 4]); // => [1, 2, 'NEW', 3, 4]
185
186
// Insert multiple elements
187
R.insertAll(2, ['X', 'Y'], [1, 2, 3, 4]); // => [1, 2, 'X', 'Y', 3, 4]
188
```
189
190
### remove, update
191
Modify list elements.
192
193
```javascript { .api }
194
// Remove elements (start index, count)
195
R.remove(2, 1, [1, 2, 3, 4, 5]); // => [1, 2, 4, 5]
196
R.remove(1, 3, [1, 2, 3, 4, 5]); // => [1, 5]
197
198
// Update element at index
199
R.update(1, 'NEW', ['a', 'b', 'c']); // => ['a', 'NEW', 'c']
200
R.update(-1, 'LAST', ['a', 'b', 'c']); // => ['a', 'b', 'LAST']
201
```
202
203
### adjust
204
Transform element at specific index.
205
206
```javascript { .api }
207
/**
208
* @param {Number} index - Position to modify
209
* @param {Function} fn - Transformation function
210
* @param {Array} list - List to modify
211
* @returns {Array} New list with element transformed
212
*/
213
R.adjust(index, fn, list)
214
215
R.adjust(1, R.toUpper, ['a', 'b', 'c']); // => ['a', 'B', 'c']
216
R.adjust(-1, R.multiply(10), [1, 2, 3]); // => [1, 2, 30]
217
```
218
219
## Slicing and Partitioning
220
221
### slice
222
Extract portion of list.
223
224
```javascript { .api }
225
/**
226
* @param {Number} from - Start index (inclusive)
227
* @param {Number} to - End index (exclusive)
228
* @param {Array} list - List to slice
229
* @returns {Array} Extracted portion
230
*/
231
R.slice(from, to, list)
232
233
R.slice(1, 3, [1, 2, 3, 4, 5]); // => [2, 3]
234
R.slice(2, -1, [1, 2, 3, 4, 5]); // => [3, 4]
235
R.slice(0, 2, 'hello'); // => 'he'
236
```
237
238
### take, takeLast, drop, dropLast
239
Take or drop elements from list boundaries.
240
241
```javascript { .api }
242
// Take from start
243
R.take(3, [1, 2, 3, 4, 5]); // => [1, 2, 3]
244
R.take(2, 'hello'); // => 'he'
245
246
// Take from end
247
R.takeLast(3, [1, 2, 3, 4, 5]); // => [3, 4, 5]
248
249
// Drop from start
250
R.drop(2, [1, 2, 3, 4, 5]); // => [3, 4, 5]
251
252
// Drop from end
253
R.dropLast(2, [1, 2, 3, 4, 5]); // => [1, 2, 3]
254
```
255
256
### takeWhile, dropWhile
257
Take/drop based on predicate.
258
259
```javascript { .api }
260
const isLessThan5 = x => x < 5;
261
262
R.takeWhile(isLessThan5, [1, 2, 6, 7, 3]); // => [1, 2]
263
R.dropWhile(isLessThan5, [1, 2, 6, 7, 3]); // => [6, 7, 3]
264
```
265
266
### splitAt, splitEvery
267
Split lists at specific points.
268
269
```javascript { .api }
270
// Split at index
271
R.splitAt(2, [1, 2, 3, 4, 5]); // => [[1, 2], [3, 4, 5]]
272
R.splitAt(3, 'hello'); // => ['hel', 'lo']
273
274
// Split into chunks
275
R.splitEvery(2, [1, 2, 3, 4, 5, 6]); // => [[1, 2], [3, 4], [5, 6]]
276
R.splitEvery(3, 'abcdefgh'); // => ['abc', 'def', 'gh']
277
```
278
279
## Grouping and Aggregation
280
281
### groupBy
282
Group elements by computed key.
283
284
```javascript { .api }
285
/**
286
* @param {Function} keyFn - Function to compute grouping key (a -> String)
287
* @param {Array} list - List to group
288
* @returns {Object} Object with keys mapping to arrays of elements
289
*/
290
R.groupBy(keyFn, list)
291
292
const students = [
293
{name: 'Alice', grade: 'A'},
294
{name: 'Bob', grade: 'B'},
295
{name: 'Carol', grade: 'A'}
296
];
297
298
R.groupBy(R.prop('grade'), students);
299
// => {A: [{name: 'Alice', grade: 'A'}, {name: 'Carol', grade: 'A'}],
300
// B: [{name: 'Bob', grade: 'B'}]}
301
302
R.groupBy(R.length, ['cat', 'dog', 'elephant', 'ox']);
303
// => {'2': ['ox'], '3': ['cat', 'dog'], '8': ['elephant']}
304
```
305
306
### partition
307
Split list into two arrays based on predicate.
308
309
```javascript { .api }
310
/**
311
* @param {Function} predicate - Test function (a -> Boolean)
312
* @param {Array} list - List to partition
313
* @returns {Array} Two-element array [matching, non-matching]
314
*/
315
R.partition(predicate, list)
316
317
const isEven = x => x % 2 === 0;
318
R.partition(isEven, [1, 2, 3, 4, 5, 6]); // => [[2, 4, 6], [1, 3, 5]]
319
320
R.partition(R.has('active'), [{active: true}, {}, {active: false}]);
321
// => [[{active: true}, {active: false}], [{}]]
322
```
323
324
## Combining Lists
325
326
### concat
327
Join two lists together.
328
329
```javascript { .api }
330
R.concat([1, 2], [3, 4]); // => [1, 2, 3, 4]
331
R.concat('hello', ' world'); // => 'hello world'
332
333
// Curried
334
const addSuffix = R.concat(R.__, ' Inc.');
335
addSuffix('Acme Corp'); // => 'Acme Corp Inc.'
336
```
337
338
### zip, zipWith
339
Combine corresponding elements from multiple lists.
340
341
```javascript { .api }
342
// Create pairs
343
R.zip([1, 2, 3], ['a', 'b', 'c']); // => [[1, 'a'], [2, 'b'], [3, 'c']]
344
345
// Combine with function
346
R.zipWith(R.add, [1, 2, 3], [4, 5, 6]); // => [5, 7, 9]
347
R.zipWith(R.concat, ['a', 'b'], ['1', '2']); // => ['a1', 'b1']
348
```
349
350
## Uniqueness and Deduplication
351
352
### uniq, uniqBy, uniqWith
353
Remove duplicates using different equality strategies.
354
355
```javascript { .api }
356
// Remove duplicates (R.equals)
357
R.uniq([1, 1, 2, 2, 3]); // => [1, 2, 3]
358
R.uniq([1, '1', 2, '2']); // => [1, '1', 2, '2']
359
360
// Remove duplicates by computed value
361
R.uniqBy(Math.abs, [-1, 1, -2, 2, 3]); // => [-1, -2, 3]
362
R.uniqBy(R.prop('id'), [{id: 1, name: 'A'}, {id: 2, name: 'B'}, {id: 1, name: 'C'}]);
363
// => [{id: 1, name: 'A'}, {id: 2, name: 'B'}]
364
365
// Remove duplicates with custom equality
366
const sameLength = (a, b) => a.length === b.length;
367
R.uniqWith(sameLength, ['cat', 'dog', 'bat', 'fox']); // => ['cat', 'dog']
368
```
369
370
## Generation Functions
371
372
### range
373
Create array of numbers from start to end (exclusive).
374
375
```javascript { .api }
376
/**
377
* @param {Number} from - Starting number (inclusive)
378
* @param {Number} to - Ending number (exclusive)
379
* @returns {Array} Array of numbers
380
*/
381
R.range(from, to)
382
383
R.range(1, 5); // => [1, 2, 3, 4]
384
R.range(0, 3); // => [0, 1, 2]
385
R.range(5, 5); // => []
386
387
// Useful for iterations
388
R.map(R.multiply(2), R.range(1, 6)); // => [2, 4, 6, 8, 10]
389
```
390
391
### times
392
Call function n times, collecting results in array.
393
394
```javascript { .api }
395
/**
396
* @param {Function} fn - Function to call with index (Number -> a)
397
* @param {Number} n - Number of times to call
398
* @returns {Array} Array of results
399
*/
400
R.times(fn, n)
401
402
R.times(R.identity, 5); // => [0, 1, 2, 3, 4]
403
R.times(R.always('x'), 3); // => ['x', 'x', 'x']
404
R.times(x => x * x, 4); // => [0, 1, 4, 9]
405
406
// Generate test data
407
R.times(() => Math.random(), 3); // => [0.1, 0.8, 0.3] (example)
408
```
409
410
## Flattening Operations
411
412
### flatten
413
Completely flatten nested arrays at all levels.
414
415
```javascript { .api }
416
/**
417
* @param {Array} list - Nested array to flatten
418
* @returns {Array} Completely flattened array
419
*/
420
R.flatten(list)
421
422
R.flatten([1, [2, [3, [4]]]]); // => [1, 2, 3, 4]
423
R.flatten([[1, 2], [3, 4], [5]]); // => [1, 2, 3, 4, 5]
424
R.flatten([1, 2, 3]); // => [1, 2, 3] (already flat)
425
```
426
427
### unnest
428
Remove one level of nesting (shallow flatten).
429
430
```javascript { .api }
431
/**
432
* @param {Array} list - Array to unnest one level
433
* @returns {Array} Array with one level removed
434
*/
435
R.unnest(list)
436
437
R.unnest([[1, 2], [3, 4], [5]]); // => [1, 2, 3, 4, 5]
438
R.unnest([1, [2, [3, 4]]]); // => [1, 2, [3, 4]]
439
R.unnest([1, 2, 3]); // => [1, 2, 3] (no nesting)
440
```
441
442
## Advanced Operations
443
444
### chain (flatMap)
445
Map and flatten in one operation.
446
447
```javascript { .api }
448
/**
449
* @param {Function} fn - Function that returns a list (a -> [b])
450
* @param {Array} list - List to map over
451
* @returns {Array} Flattened result
452
*/
453
R.chain(fn, list)
454
455
const duplicate = x => [x, x];
456
R.chain(duplicate, [1, 2, 3]); // => [1, 1, 2, 2, 3, 3]
457
458
R.chain(R.split(''), ['hello', 'world']); // => ['h','e','l','l','o','w','o','r','l','d']
459
```
460
461
### aperture
462
Create sliding windows of consecutive elements.
463
464
```javascript { .api }
465
/**
466
* @param {Number} size - Window size
467
* @param {Array} list - List to window
468
* @returns {Array} Array of windows
469
*/
470
R.aperture(size, list)
471
472
R.aperture(2, [1, 2, 3, 4, 5]); // => [[1,2], [2,3], [3,4], [4,5]]
473
R.aperture(3, [1, 2, 3, 4, 5]); // => [[1,2,3], [2,3,4], [3,4,5]]
474
```
475
476
### transpose
477
Flip rows and columns of 2D array.
478
479
```javascript { .api }
480
R.transpose([[1, 'a'], [2, 'b'], [3, 'c']]);
481
// => [[1, 2, 3], ['a', 'b', 'c']]
482
483
R.transpose([[1, 2, 3], ['a', 'b', 'c']]);
484
// => [[1, 'a'], [2, 'b'], [3, 'c']]
485
```
486
487
## Validation Functions
488
489
### all, any, none
490
Test predicates across list elements.
491
492
```javascript { .api }
493
// All elements match
494
R.all(x => x > 0, [1, 2, 3]); // => true
495
R.all(x => x > 0, [1, -1, 3]); // => false
496
497
// Any element matches
498
R.any(x => x > 10, [1, 15, 3]); // => true
499
R.any(x => x > 10, [1, 5, 3]); // => false
500
501
// No elements match
502
R.none(x => x < 0, [1, 2, 3]); // => true
503
R.none(x => x < 0, [1, -1, 3]); // => false
504
```
505
506
### includes
507
Check if element exists in list.
508
509
```javascript { .api }
510
R.includes(3, [1, 2, 3, 4]); // => true
511
R.includes('world', 'hello world'); // => true
512
R.includes({a: 1}, [{a: 1}, {b: 2}]); // => true (deep equality)
513
```
514
515
These list functions provide the foundation for functional programming patterns in JavaScript, enabling powerful data transformations while maintaining immutability and composability.