Comments (21)
@Ne4to777: Are you simply trolling here?
It's well-known that JS has low recursion stack limits. Last I knew (maybe 2019) most browsers were in the 10,000 - 20,000 call range, except that Safari went to 30,000. Moreover, although tail-call optimization has been specified since ES2015, almost all engines are ignoring this. So one cannot run recursive code against large data. And even against smaller data, the overhead is often performance-prohibitive. (For a case study, see Eweda, the predecessor to Ramda, which had elegant recursive code but couldn't perform.)
Recursion is a much cleaner way to write FP code; it can be done without variable reassignment, and often much more simply than its imperative alternatives. But since we cannot use it in JS unless we know the data is fairly small, we can't use it to build libraries.
from fantasy-land.
@Ne4to777 You seem to be missing the fact that the fantasy-land interoperability specification is, despite the name, no pipe dream of tomorrow but rather a practical tool for today.
If you want to discuss theoretical concepts, there are better venues than this issue tracker.
from fantasy-land.
Аnd this is why "reduce" will always be a problem
Why is that? It's not obvious to me.
the code inside was difficult to write through composition, so you wrote it imperatively. Therefore, the FP dies.
I am very confused about the flow of the conversation.
For starter, ultimately, if you find some code unsatisfactory, you... fix the code and open a pull request?
Another thing is, I dont think "the code is in x style" is a good argument. people write code as an mean, not as an end.
"The code has error/is complex/inefficient/make reasoning hard because it screw up invariance“ is some of them, but "the code is written in imperative style" isnt really one IMO. (yes, mutable reference screw invariance and reasoning hard, but the code you object to is only using local variable). You can rewrite it with state monad or with recursion in general... but the code is "the same" - you only push the reasoning complexity inside the monad/the call stack.
And at the end of the line, "all code should be written using FP" is just a weird assumption. There are a plethora of domain out there, that can be written by one single person, but the SOTA isnt written in FP. Some example is chess engine, egraph, linear algebra, HPC. If fp die here, fp is dead everywhere.
from fantasy-land.
PLONK
from fantasy-land.
I really don't understand
Fantasy Land specifies a simulation of type classes (an FP feature) in JavaScript. The closest it can get to functional type classes in a language which doesn't support them natively, is to specify classical interfaces (in text, not code, because JavaScript also doesn't have interfaces).
These classical interfaces are most easily and conveniently implemented in JavaScript via classical classes (using this
and stuff), but they don't have to be. There are various libraries out there which have values that conform to these Fantasy Land interfaces which were constructed without the use of new
or this
.
For example, Sanctuary uses Object.create
to create object structures like:
{
value: 42,
__proto__: {
isJust: true,
'fantasy-land/map': function(f){ return Just(f(this)) }
//...
}
}
So Sanctuary doesn't use classes or new
, but does use this
.
It's also possible to conform to the Fantasy Land interfaces without using any this
or new
:
const Identity = value => ({
value,
'fantasy-land/map': f => Identity(f(value)),
constructor: {
'fantasy-land/of': x => Identity(x)
}
})
So Fantasy Land does not inherently condone or condemn the use of such features, but having to simulate type classes through interfaces leads to a solution which naturally aligns well with the classical object oriented model. As a library author, you can choose to benefit from this alignment, but you don't have to. Finally, users of Fantasy Land compliant libraries don't typically notice either way: as a consumer of a FL-compliant lib you don't need to use any OOP features.
from fantasy-land.
Well, even if all the developers of FP libraries write in OOP, why should other developers use FP? Therefore, the total defeat of the FP on all fronts is evident. The only thing that is widely used is composition. I've written a couple of examples, so what's the problem?
// of :: Applicative f => a -> f a
export const of = x => () => x
// extract :: Comonad w => w a ~> () -> a
export const extract = wa => wa()
// map :: Functor f => f a ~> (a -> b) -> f b
export const map = fa => g => of(g(extract(fa)))
// contramap :: Contravariant f => f a ~> (b -> a) -> f b
export const contramap = fa => g => of(x => extract(fa)(g(x)))
// ap :: Apply f => f a ~> f (a -> b) -> f b
export const ap = fa => fg => of(extract(fg)(extract(fa)))
// chain :: Chain m => m a ~> (a -> m b) -> m b
export const chain = ma => g => g(extract(ma))
// extend :: Extend w => w a ~> (w a -> b) -> w b
export const extend = wa => g => of(g(wa))
// compose :: Semigroupoid c => c i j ~> c j k -> c i k
export const compose = cij => cjk => of(x => extract(cjk)(extract(cij)(x)))
from fantasy-land.
Well, even if all the developers of FP libraries write in OOP, why should other developers use FP?
Many people find the functions provided by Sanctuary and similar libraries quite natural:
> S.map (Math.sqrt) ([1, 4, 9])
[1, 2, 3]
> S.map (Math.sqrt) (S.Nothing)
Nothing
> S.map (Math.sqrt) (S.Just (64))
Just (8)
> S.map (Math.sqrt) (S.Left ('XXX'))
Left ('XXX')
> S.map (Math.sqrt) (S.Right (100))
Right (10)
> S.map (Math.sqrt) (S.Pair ('foo') (1024))
Pair ('foo') (32)
Someone using S.map
need not be concerned with its implementation.
from fantasy-land.
Well, even if all the developers of FP libraries write in OOP, why should other developers use FP?
Many people find the functions provided by Sanctuary and similar libraries quite natural:
Someone using
S.map
need not be concerned with its implementation.
These are particular examples. And there really is nothing criminal about them. But can you show an exemplary FP program? So far, I only see terrible OOP-FP mutants.
from fantasy-land.
I'm pleased that you do not find Haskell's fmap
function criminal. 😜
You may find concatFiles
and program
(and their surrounding code) interesting.
from fantasy-land.
you held on well, but then something went wrong :) https://github.com/sanctuary-js/sanctuary-site/blob/ac68f7cbd1c541cfa653089b815cc4e1ae08b3b5/scripts/generate#L340
Аnd this is why "reduce" will always be a problem: https://github.com/sanctuary-js/sanctuary-site/blob/ac68f7cbd1c541cfa653089b815cc4e1ae08b3b5/scripts/generate#L568
from fantasy-land.
Аnd this is why "reduce" will always be a problem
Why is that? It's not obvious to me.
from fantasy-land.
Аnd this is why "reduce" will always be a problem
Why is that? It's not obvious to me.
the code inside was difficult to write through composition, so you wrote it imperatively.
Therefore, the FP dies.
from fantasy-land.
It's really unclear why you are contrasting the usage of objects with functional programming as if they were mutually exclusive.
from fantasy-land.
It's really unclear why you are contrasting the usage of objects with functional programming as if they were mutually exclusive.
it's not just about objects, but about the context of objects. In js, there are three ways to pass variables into a function: arguments, global variables, and context. Functional programming is just arguments and nothing else.
from fantasy-land.
Functional programming can use this
and new
. They don't break functions.
They may or may not be "OOP features" - whatever that means. Nobody cares.
from fantasy-land.
Functional programming can use
this
andnew
. They don't break functions.
No, it can`t. Otherwise call it FOOP.
from fantasy-land.
Care to give the definitive definition of FP and OOP and then use them to explain why FP code cannot interact with OOP code?
Аnd this is why "reduce" will always be a problem
Why is that? It's not obvious to me.
the code inside was difficult to write through composition, so you wrote it imperatively. Therefore, the FP dies.
JS's poor recursion support means that many things cannot be written internally as cleanly as they might be in, say, Haskell. That doesn't mean they don't support an API that is FP.
from fantasy-land.
@CrossEye , what do you mean by poor support?
from fantasy-land.
@CrossEye , You said about browsers, but what does this have to do with javascript? Or then show me infinite recursion in Haskell in any browser.
We are discussing the concept, not the implementation. The scarcity of resources today should not kill the theory of tomorrow.
You put the question like this: why do we need to use JS because it is bad in FP?
And I’m like this: since we are using JS in FP, then why we break the rules that we can not break?
from fantasy-land.
@bergus , that is, is it okay to use context in a contextless paradigm?
from fantasy-land.
We are discussing the concept, not the implementation. The scarcity of resources today should not kill the theory of tomorrow.
I have no idea what you're discussing. Most of us here are discussing a specification for data types with useful commonalities.
Moreover, a specification that cannot be implemented due to practical concerns is simply a work of fantasy.
from fantasy-land.
Related Issues (20)
- [Question] Type signature for ap HOT 2
- Adding Folktale to implementations.md
- Equivalent for Serial typeclass? HOT 1
- Is really necessary specify "No parts of <...> value should be checked"? HOT 11
- Add Traversable1 HOT 3
- Help understanding use of identity in Traversable laws HOT 2
- Fantasy Land specification version number HOT 1
- Switch to Symbols HOT 2
- Wrong argument in Traversable HOT 4
- Is monet.js compatible? HOT 1
- Why FL specifies the ChainRec typeclass when there is the trampoline monad? HOT 7
- What does "and" mean? HOT 2
- Can someone explain me how I should understand Semigroup? HOT 5
- Traversable and Foldable use multiple variables as arguments HOT 12
- Profunctor should require Contravariant HOT 10
- Implementation of `Compose` is confusing HOT 3
- should Chain properties depends on fantasy-land/ap (and possibly .map)? HOT 4
- Why putting "fantasy-land/" before everything in readme? HOT 3
- Is `Pair` a valid instance of `MonadRec`?
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from fantasy-land.