Skip to content

Commit

Permalink
start reduce by
Browse files Browse the repository at this point in the history
  • Loading branch information
Deyan Totev committed Dec 20, 2023
1 parent fe0b6b1 commit 558b2ac
Show file tree
Hide file tree
Showing 4 changed files with 194 additions and 122 deletions.
2 changes: 2 additions & 0 deletions NEXT_VERSION_CHECKLIST.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ git push origin v8.6.0

issue with gh release
---
throttle should accept 0 arguments, i.e. no need to force unary function
---
include standut x methods to rambda

such as
Expand Down
14 changes: 11 additions & 3 deletions files/index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5726,7 +5726,7 @@ Example:
```
```
Categories:
Categories: Number
Notes:
Expand All @@ -5744,7 +5744,7 @@ Example:
```
```
Categories:
Categories: Number
Notes:
Expand All @@ -5762,7 +5762,7 @@ Example:
```
```
Categories:
Categories: List
Notes:
Expand Down Expand Up @@ -7962,6 +7962,14 @@ Notes: Function input can be asynchronous
// @SINGLE_MARKER
export function partialCurry<Input, PartialInput, Output>(
fn: (input: Input) => Output,








partialInput: PartialInput,
): (input: Pick<Input, Exclude<keyof Input, keyof PartialInput>>) => Output;

Expand Down
18 changes: 15 additions & 3 deletions source/reduceBy.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,17 @@
export function reduceBy(foo, bar){
if (arguments.length === 1)
return _bar => reduceBy(foo, _bar)
import { has } from "./has.js";
import { curry } from "./curry.js";
import { reduce } from "./reduce.js";
import { clone } from "./clone.js";

export function reduceByFn(valueFn, valueAcc, keyFn, list){
var xf = function(acc, elt) {
var key = keyFn(elt);
var value = valueFn(has(key, acc) ? acc[key] : clone(valueAcc), elt);

acc[key] = value;
return acc;
}
return reduce(xf, {}, list);
}

export const reduceBy = curry(reduceByFn)
282 changes: 166 additions & 116 deletions source/reduceBy.spec.js
Original file line number Diff line number Diff line change
@@ -1,129 +1,179 @@
import { reduceBy as reduceByRamda } from 'ramda'

import { reduceBy } from './reduceBy.js'
import { prop } from './prop.js'

test('happy', () => {
const result = reduceBy()
console.log(result)
})

/*
var R = require('../source/index.js')
var eq = require('./shared/eq.js')
var byType = R.prop('type')
var sumValues = function (acc, obj) {
const byType = prop('type')
const sumValues = function (acc, obj){
return acc + obj.val
}

var sumInput = [
{type: 'A', val: 10},
{type: 'B', val: 20},
{type: 'A', val: 30},
{type: 'A', val: 40},
{type: 'C', val: 50},
{type: 'B', val: 60},
]
describe('reduceBy', function () {
var grade = function (score) {
return score < 65
? 'F'
: score < 70
? 'D'
: score < 80
? 'C'
: score < 90
? 'B'
: 'A'
}
var students = [
{name: 'Abby', score: 84},
{name: 'Brad', score: 73},
{name: 'Chris', score: 89},
{name: 'Dianne', score: 99},
{name: 'Eddy', score: 58},
{name: 'Fred', score: 67},
{name: 'Gillian', score: 91},
{name: 'Hannah', score: 78},
{name: 'Irene', score: 85},
{name: 'Jack', score: 69},
]
var byGrade = function (student) {
return grade(student.score || 0)
}
const grade = function (score){
return score < 65 ?
'F' :
score < 70 ?
'D' :
score < 80 ?
'C' :
score < 90 ?
'B' :
'A'
}

it('splits the list into groups according to the grouping function', function () {
var collectNames = function (acc, student) {
return acc.concat(student.name)
}
eq(R.reduceBy(collectNames, [], byGrade, students), {
A: ['Dianne', 'Gillian'],
B: ['Abby', 'Chris', 'Irene'],
C: ['Brad', 'Hannah'],
D: ['Fred', 'Jack'],
F: ['Eddy'],
})
})
const byGrade = function (student){
return grade(student.score || 0)
}

it('splits the list into mutation-free groups', function () {
var collectNames = function (acc, student) {
acc.push(student.name)
return acc
}
eq(R.reduceBy(collectNames, [], byGrade, students), {
A: ['Dianne', 'Gillian'],
B: ['Abby', 'Chris', 'Irene'],
C: ['Brad', 'Hannah'],
D: ['Fred', 'Jack'],
F: ['Eddy'],
})
test.only('splits the list into groups according to the grouping function', () => {
const collectNames = function (acc, student){
return acc.concat(student.name)
}
expect(reduceBy(
collectNames, [], byGrade, getStudents()
)).toEqual({
A : [ 'Dianne', 'Gillian' ],
B : [ 'Abby', 'Chris', 'Irene' ],
C : [ 'Brad', 'Hannah' ],
D : [ 'Fred', 'Jack' ],
F : [ 'Eddy' ],
})
})

it('returns an empty object if given an empty array', function () {
eq(R.reduceBy(sumValues, 0, byType, []), {})
})
// test('splits the list into mutation-free groups', () => {
// const collectNames = function (acc, student){
// acc.push(student.name)

it('can act as a transducer', function () {
var reduceToSumsBy = R.reduceBy(sumValues, 0)
var sumByType = reduceToSumsBy(byType)
eq(
R.into(
{},
R.compose(sumByType, R.map(R.adjust(1, R.multiply(10)))),
sumInput
),
{A: 800, B: 800, C: 500}
)
eq(
R.transduce(
R.compose(sumByType, R.map(R.adjust(1, R.multiply(10)))),
(result, input) => {
result[input[0]] = result[input[0]]
? result[input[0]]
: 0 + input[1]
return result
},
{},
sumInput
),
{A: 800, B: 800, C: 500}
)
})
// return acc
// }
// expect(reduceBy(
// collectNames, [], byGrade, getStudents(
// )).toEqual({
// A : [ 'Dianne', 'Gillian' ],
// B : [ 'Abby', 'Chris', 'Irene' ],
// C : [ 'Brad', 'Hannah' ],
// D : [ 'Fred', 'Jack' ],
// F : [ 'Eddy' ],
// })
// })

it('short circuits with reduced', function () {
var collectNames = function (acc, student) {
return student.name === 'Fred'
? R.reduced(acc)
: acc.concat(student.name)
}
eq(R.reduceBy(collectNames, [], byGrade, students), {
A: ['Dianne'],
B: ['Abby', 'Chris'],
C: ['Brad'],
F: ['Eddy'],
})
})
test('returns an empty object if given an empty array', () => {
expect(reduceBy(
sumValues, 0, byType, []
)).toEqual({})
})

*/
// test('can act as a transducer', () => {
// const reduceToSumsBy = reduceBy(sumValues, 0)
// const sumByType = reduceToSumsBy(byType)
// expect(R.into(
// {},
// R.compose(sumByType, R.map(R.adjust(1, R.multiply(10)))),
// sumInput
// )).toEqual({
// A : 800,
// B : 800,
// C : 500,
// })
// expect(R.transduce(
// R.compose(sumByType, R.map(R.adjust(1, R.multiply(10)))),
// (result, input) => {
// result[ input[ 0 ] ] = result[ input[ 0 ] ] ? result[ input[ 0 ] ] : 0 + input[ 1 ]

// return result
// },
// {},
// sumInput
// )).toEqual({
// A : 800,
// B : 800,
// C : 500,
// })
// })

// test('short circuits with reduced', () => {
// const collectNames = function (acc, student){
// return student.name === 'Fred' ?
// R.reduced(acc) :
// acc.concat(student.name)
// }
// expect(reduceBy(
// collectNames, [], byGrade, getStudents(
// )).toEqual({
// A : [ 'Dianne' ],
// B : [ 'Abby', 'Chris' ],
// C : [ 'Brad' ],
// F : [ 'Eddy' ],
// })
// })

function getStudents(){
return [
{
name : 'Abby',
score : 84,
},
{
name : 'Brad',
score : 73,
},
{
name : 'Chris',
score : 89,
},
{
name : 'Dianne',
score : 99,
},
{
name : 'Eddy',
score : 58,
},
{
name : 'Fred',
score : 67,
},
{
name : 'Gillian',
score : 91,
},
{
name : 'Hannah',
score : 78,
},
{
name : 'Irene',
score : 85,
},
{
name : 'Jack',
score : 69,
},
]
}

function getSumInput (){
return [
{
type : 'A',
val : 10,
},
{
type : 'B',
val : 20,
},
{
type : 'A',
val : 30,
},
{
type : 'A',
val : 40,
},
{
type : 'C',
val : 50,
},
{
type : 'B',
val : 60,
},
]
}

0 comments on commit 558b2ac

Please sign in to comment.