-
Notifications
You must be signed in to change notification settings - Fork 205
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Proposal: Introduce <- operator for clean and composable transformations #4170
Comments
While different suggested syntax, it might be related to / duplicate of: #1246 |
Agree, this is another infix reverse-order function application operator, aka "pipe". (So closing and deferring to the existing issue, which should now have a link back to here.) The arrow direction feels wrong to me, probably because I think in "data flow" order. The value flows into the function, its result flows into the next function, etc. This arrow points in the opposite direction. The operator e1 <- e2 <- e3 would be let v1 = e1 in let v2 = e2(v1) in e3(v2) (If Dart had a I personally prefer |
Thank you for reviewing, I agree, it looks duplicate. |
Just in case somebody is wondering, the following functional style is already possible: "someString"
.toUpperCase()
.map((s) => '$s is amazing')
.print(); Minimal example: import 'dart:core';
import 'dart:core' as core;
void main() {
"someString"
.print()
.toUpperCase()
.print()
.map((s) => '$s is amazing')
.print()
.appendExclamation()
.print();
}
extension on String {
String appendExclamation() => this+"!";
String map(String f(String input)) => f(this);
}
extension Printer<T> on T {
T print() {
core.print(this);
return this;
}
} More examples: import 'dart:core';
import 'dart:core' as core;
void main() {
print( 1.plus(2).plus(3) );
print( 2.5.plus(2.6) );
1.plus(2).plus(3).print();
2.5.plus(2.6).print();
("-"*30).print();
"aBcDeFg".toUpperCase().appendExclamation().print();
("-"*30).print();
100.print();
1.1.print();
(1,2).print();
("-"*30).print();
(8,7).add().print();
(1.5,2.5).add().print();
("-"*30).print();
final numbers = [1, 5, 10, 100];
final result1 = numbers.map((num) => num * 3);
result1.print();
[1, 5, 10, 100].map((num) => num * 4).print();
("-"*30).print();
"someString"
.toUpperCase()
.map((s) => '$s is amazing')
.appendExclamation()
.print();
"someString"
.print()
.toUpperCase()
.print()
.map((s) => '$s is amazing')
.print()
.appendExclamation()
.print();
("-"*30).print();
// Handling curried functions
var curriedAdd = (x) => (y) => add(x, y);
var result2 = curriedAdd(6)(11); // Result: 17
var result3 = 5.curriedAdd(10); // Result: 15
result2.print();
result3.print();
}
num add(num x, num y) => x + y;
extension on num {
num plus(num x) => this + x;
num curriedAdd(y) => add(this, y);
}
extension on String {
String appendExclamation() => this+"!";
String map(String f(String input)) => f(this);
}
extension Printer<T> on T {
T print() {
core.print(this);
return this;
}
}
extension on (num,num) {
num add() => this.$1 + this.$2;
} |
Abstract
This proposal suggests adding the <- operator to Dart to facilitate concise and readable functional transformations. The operator allows for left-to-right application of functions to values, enhancing code composability and readability without adding undue complexity.
Motivation
Dart lacks a concise syntax for chaining value transformations in a functional style. While the cascade operator (..) aids in object configuration (similar to Kotlin's apply), there is no equivalent for transforming values (like Kotlin's let). Introducing the <- operator addresses this gap, allowing developers to write more expressive and maintainable code.
Proposal Details
Syntax
expression <- function
Behavior
Examples
Benefits
Compare:
print(appendExclamation(toUpperCase(someString)));
vs
someString <- toUpperCase <- appendExclamation <- print;
Choice of <-
Precedence
What do you think?
Thanks!
The text was updated successfully, but these errors were encountered: