Where communities thrive


  • Join over 1.5M+ people
  • Join over 100K+ communities
  • Free without limits
  • Create your own community
People
Repo info
Activity
  • Jan 31 2019 22:17
    CrossEye commented #2779
  • Jan 31 2019 21:04
    ArturAralin commented #2779
  • Jan 31 2019 20:08
    CrossEye commented #2779
  • Jan 31 2019 18:56
    buzzdecafe commented #2631
  • Jan 31 2019 18:09
    ArturAralin commented #2779
  • Jan 31 2019 16:18
    CrossEye commented #2779
  • Jan 31 2019 16:10
    CrossEye commented #2631
  • Jan 31 2019 16:06
    CrossEye commented #2777
  • Jan 31 2019 14:44
    ArturAralin opened #2779
  • Jan 31 2019 07:39
    inferusvv commented #2631
  • Jan 31 2019 03:07
    sespinozj commented #2771
  • Jan 31 2019 02:33
    machad0 commented #2771
  • Jan 31 2019 02:26
    JeffreyChan commented #2777
  • Jan 30 2019 14:30
    CrossEye closed #2777
  • Jan 30 2019 12:13
    vanyadymousky updated the wiki
  • Jan 30 2019 01:42
    JeffreyChan commented #2777
  • Jan 29 2019 21:06
    vanyadymousky updated the wiki
  • Jan 29 2019 16:28
    CrossEye commented #2777
  • Jan 29 2019 15:50
    mbostock commented #2772
  • Jan 29 2019 15:48
    CrossEye commented #2772
trbrc
@trbrc
R.last(R.sortBy(fn, list)) ? maybe it's that simple.
Scott Sauyet
@CrossEye
.... although a sort just to find a max sounds like the wrong algorithm. If the data is small enough that should be fine.
Simon Friis Vindum
@paldepind
I agree that the current code is quite convoluted.
trbrc
@trbrc
i guess what i mean is that it feels a bit like a puzzle to me. it's easy to lose track and get lost.
this should probably be done better using reduce.
if i write the same code using a for loop i don't really need to think about it, all the stuff i need to look at is right there.
but maybe it's just because i've been writing imperative code for so long.
Scott Sauyet
@CrossEye
There definitely is an adjustment period.
But note that this can be written fairly simply as R.useWith(R.reduce, R.maxBy). http:// bit.ly/1KnFLGv
trbrc
@trbrc
thanks, i just rewrote it using reduce, but i would never have figured out that i could use useWith.
so i guess at least part of my issue that i have not yet internalized the different building blocks i might use to solve a problem.
so I end up using the wrong ones.
Scott Sauyet
@CrossEye
useWith and converge are oddballs. Don't feel bad at all about not thinking about them. They are quite useful though when you get to know them.
trbrc
@trbrc
maybe part of it is that it's hard to put words on what some of these functions do. like, "use with" could mean a lot of things.
it seems like a lot of functional programming tools deal with these patterns underlying what you're trying to do. they're not always so easy to see.
Scott Sauyet
@CrossEye
And we need very soon to have our summit on the various compose-related functions. They've become something of a mess.
hemanth.hm
@hemanth
Trying to reduce:
R.uniq(R.keys(R.values(R.pick(['name','age'],data))[0])).sort()
David Chambers
@davidchambers
Rather than R.values(R.pick(['name', 'age'], data)) you could use R.props(['name', 'age'], data).
hemanth.hm
@hemanth
Nice, so it's like R.keys(R.prop(['name'],data)).sort()
Can keys + sort be composed into one single function?
Scott Christopher
@scott-christopher
@hemanth Try R.compose(R.sortBy(R.identity), R.keys)
hemanth.hm
@hemanth
@scott-christopher Nice, but it's not doing a natural sort.
Scott Christopher
@scott-christopher
If you want specific sorting behaviour you can use R.sort and provide your own comparator function instead.
hemanth.hm
@hemanth
hmm, was thinking of the same, cool, will stick with R.prop for now.
Alex Afonin
@Tuch
Guys, maybe someone use ramba a with flux? Need examples :)
Examples of big app.. With many entities..
Sergey Rubanov
@chicoxyzzy
@Tuch there are not so much examples of big apps open sourced. btw I use Ramda with Alt (but I plan to migrate to lodash-fp in future)
Alex Afonin
@Tuch
Hm. Ok, thanks you, will try too
Jason Heard
@101100

I'm trying to do something without writing the keyword function (i.e. creating the function using R.* as an exercise). The goal is a function that takes two arguments, the first is a list of ids, the second is a list of objects (with an id property). The function should return the items from the second list that have ids from the first list. Here is a small working example (with one use of function):

var a = [ 1, 2, 3 ];
var b = [ {id: 1, b: 'Yay!' }, { id: 3, b: 'Oh yeah!' }, { id: 4, b: 'Oh noes!' } ];

var answerFunc = function (x, y) { R.pipe(R.map(R.pipe(R.unary(R.propEq('id')), R.partialRight(R.find, y))), R.filter(R.identity))(x) };

answerFunc(a, b);
// -> [ { id: 1, b: 'Yay!' }, { id: 3, b: 'Oh yeah!' } ]

I can't figure out how to "extract" the y parameter from the middle so I can say something like:

var answerFunc = R....

Any ideas?

Aldwin Vlasblom
@Avaq
@101100 R.useWith(R.filter, R.useWith(R.pipe, R.always(R.prop('id')), R.flip(R.contains))(null), R.identity)
A little bit hacky, I couldn't find an easy way to push a into R.flip(R.contains) without affecting the composition with R.prop('id'). So now I'm calling R.always(R.prop('id')) with null.
But it works. :P
Aldwin Vlasblom
@Avaq
"Extracting the parameter from the middle" like you said is done with R.useWith or R.converge (if I understand you correctly).

Basically:
converge(f, a, b)(x, y) === f(a(x, y), b(x, y))
useWith(f, a, b)(x, y) === f(a(x), b(y))

So the passed in variable makes its way "deeper" into "the middle".

Jason Heard
@101100
@Avaq Thanks for the solution and explanation!
Jason Heard
@101100
I managed to remove the (null) hack: R.useWith(R.filter, R.pipe(R.unary(R.flip(R.contains)), R.partial(R.pipe, R.prop('id'))), R.identity), but I'm not sure if it is "better".
Aldwin Vlasblom
@Avaq
Certainly interesting, using partial to prepare a pipeline for its final function, I would never have thought of that. It's still a little convoluted, but I would say it's an improvement as there's no more artificial noop in there (always(x)(null) to get x :P ).
Scott Sauyet
@CrossEye
@101100: If you're doing this as a learning experience, it's an interesting exercise. But I would not make a fetish out of points-free. I think the following version is much more readable. (Of course the es6 syntax helps.):
((a, b) => R.chain(id => R.filter(R.propEq('id', id), b), a))
hemanth.hm
@hemanth
under what license is web ramda-repl ?
Aldwin Vlasblom
@Avaq

@CrossEye Agreed, I do believe this was meant to be an exercise though. :)

And coming back to it, @101100, I've found another way around the (null)-hack, much closer to my original plan. My first try was R.converge(R.compose, R.flip(R.contains), R.always(R.prop('id'))), but that returned a 2-ary function and I didn't understand why (it should only take in a). So I looked at the converge source today and noticed it chooses its arity based on the highest arity from the input functions, which was 2 for R.flip(R.contains). So the fix was to flag it as unary, so the complete thing becomes:

R.useWith(R.filter, R.converge(R.compose, R.unary(R.flip(R.contains)), R.always(R.prop('id'))), R.identity);

I'm not saying it's a better solution by any means (there's still a secret noop), but I did learn something new about converge I wanted to share. :)

Raine Virta
@raine
how do you map over a return value of a function that returns a thenable in pipe? is there a ramda function that checks for .then?
it used to be possible to use pipeP so that not all functions returned a Promise
Raine Virta
@raine
ramda/ramda#1314
Raine Virta
@raine
const then = curry((fn, thenable) => thenable.then(fn));
const readFile = (p) => fs.readFileAsync(p, 'utf8');
const getStuff = pipe(formatPath, readFile, then(toUpper));
there's probably a better way than coming up with a map (the then) specific to promises
Danielle McLean
@00dani
Well, typewise R.chain should be the right function for "mapping" promises. Of course, the standard promise API is incompatible with fantasy-land's monad definitions so it doesn't quite work out.
Martin Algesten
@algesten

I was trying to parse xml data using cheerio/jQuery the other day and it struck me how awkward those libraries are for functional programming.

So I decided to learn top down operator precedence-parsers and applied it to parsing CSS-expressions. End result is an attempt to make a lightweight tool for reading XML/HTML in a functional style. https://github.com/algesten/zu

Now I want it to work really well with Ramda, but I'm a bit stuck on currying. I want to have zu.parents(nodes, 'div > span') be curried as zu.parents('div > span')(nodes) but maybe also zu.parents(nodes)('div > span') but then that last form is not possible since i may also want zu.parents(nodes)as a one-arg version (just parents without an expression).

Does any of you fine minds have any thoughts on that currying conundrum?

jeffcato
@jeffcato
does ramda have an abstraction for switch or if/else that would make sense to use here?:
switch(req.method) { 
    case 'GET': 
        getCacheKey(cache, url).fork(
            function(err) {
                getDocuments(getCollection(db, collectionName)).fork(
                    send404(res), 
                    sendPage(res, cache, collectionName, url)
                );
            },
            function(value) {
                console.log('sent cached value'); 
                res.end(value); 
            }
        ); 
        break;
    case 'POST':
        // handle post req's
        break;
    default:
        send404(res, null); 
        break;
}
Scott Sauyet
@CrossEye
@algesten: raganwald does this by offering a second version of many functions, suffixed with 'With'. So parents(selector)(nodes) and parentsWith(nodes)(selector) or vice versa.
jeffcato
@jeffcato
or possibly a monad in ramda-fantasy could handle it better?
i'm pretty new to functional programming in general so forgive me if this is obvious