Comments (10)
It would be even better with C++14: it has closures that can automatically capture by reference and automatically type themselves
from ts2c.
If I wanted to implement closures via outputting a superset of C, which files of this project would I need to change?
from ts2c.
@CrazyPython there's an extended readme under "src" folder that describes file purposes and approaches used in implementation: https://github.com/andrei-markeev/ts2c/tree/master/src
@brunobasto started implementing anonymous functions, see his commit e22121b, it might help you to get some understanding of the scope.
Closures can be easily expressed with nested functions in C. Nesting functions isn't a part of standard, but it is supported by gcc so it might be a viable approach for basic implementation.
So for example you have this code:
var sum = 0;
var k = 2;
var add = function(n) { sum += n * k; }
add(30);
console.log(sum);
then the corresponding C code could look something like this:
int16_t sum, k;
int main() {
int16_t add(int16_t n) {
sum += n * k;
}
sum = 0;
k = 2;
add(30);
printf("%d\n", sum);
}
But if we want to keep to the standard only (which I believe is important, because I believe there could be some toolchain implementations that don't support nested functions), then the easiest way would probably be to try to lift the variables into global scope, changing their name so that it doesn't conflict with any existing variables. This is not efficient memory-wise though, and memory consumption is quite important on embedded devices.
So most likely the best way to do it is to
- Detect which variables from current scope are used inside function expression
- Add those variables as parameters to the function (and if they're changed inside this function, then they should be passed by reference)
So the example above will probably compile to something like this:
int16_t add(int16_t n, int16_t* sum, int16_t k) {
*sum += n * k;
}
int16_t sum, k;
int main() {
sum = 0;
k = 2;
add(30, &sum, k);
printf("%d\n", sum);
}
Obviously this approach is quite hard to implement and requires changes in types detection and memory management.
from ts2c.
int16_t sum, k;
int main() {
int16_t add(int16_t n) {
sum += n * k;
}
add(30);
printf("%d\n", sum);
}
It won't return a function correctly.
from ts2c.
well passing pointers to the function is a whole different story... but in fact I think it will work fine with nested functions, for example this code works fine:
int16_t sum, k;
void *test1() {
int16_t add(int16_t n) {
sum += n * k;
}
sum = 0;
k = 2;
add(30);
printf("1. %d\n", sum);
return &add;
}
int main() {
int16_t (*add_func)(int) = test1();
(*add_func)(5);
printf("2. %d\n", sum);
}
corresponds to the following TS code:
var sum = 0;
var k = 2;
function test() {
var add = function(n) { sum += n * k; }
add(30);
console.log("1.",sum);
return add;
}
var add_func = test();
add_func(5);
console.log("2.",sum);
If we don't use nested functions however, then your idea with struct that contains function pointer and closure parameters becomes the valid one. So ultimately this is what we would have to do, yes.
from ts2c.
somewhat unrelated question: does ts2c support function pointers? (I have an existing application where a closure is created inside a class, and it assigns that closure inside the constructor.)
from ts2c.
not currently
in COVERAGE.md, this whole feature - closures + function pointers, is referred to as "function
inside expressions"
from ts2c.
https://github.com/fabiosantoscode/js2cpp
https://github.com/fabiosantoscode/dumbjs
It turns
function foo(x) {
x++
return function () { return x }
}
console.log(foo(0)())
Into
var _flatten_0 = function (_closure) {
return _closure.x
}
var foo = function (x) {
var _closure_0 = {}
_closure_0.x = x
_closure_0.x++
return BIND(_flatten_0, _closure_0)
}
var main = function () {
console.log(foo(0)())
}
@andrei-markeev This may be more effective
from ts2c.
This is certainly an option, however, additional transpilation step will make output code less readable, and also increase overall transpilation time. So I would rather avoid it.
from ts2c.
Closures are now implemented, even though I expect that there might still be some edge cases where it does not work. Please let me know if you notice those!
from ts2c.
Related Issues (20)
- Calling C Functions
- Feature: Classes (for TS at least) HOT 8
- Finishing ES3 features once and for all HOT 6
- Compiling TypeScript to C via WebAssembly HOT 2
- Please include the original code as a comment in the transpiled code HOT 12
- Memory allocation bug HOT 6
- Function.prototype.toString HOT 1
- C functions HOT 2
- Syntax errors are handled incorrectly
- Playground autocomplete keeps repeating
- Order in which properties are added is not honored
- Incorrect generation of 'free' call
- Using C++ instead of C? HOT 4
- npm - Unexpected end of JSON
- Error when combining "for in" and "for of"
- labelled statements don't work
- Ain't work HOT 1
- arguments array ain;t work
- problem with functions called main
- error with functions returning functions HOT 1
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 ts2c.