Open weswigham opened 10 years ago
I'm sorry but I don't really see why this is needed. Can you elaborate?
It's a shorthand for specifying things that are asynchronous - it clarifies asynchronous code far better than
spawn(proc() {
x = x + 1
})
Which is difficult to know when has been completed (without inefficient busy-loops, or nested promises/callbacks). It's never been required, per sey, it's not a necessity to use it to write async code in C#, C++, or ES6, but it makes the code you do write wit it far easier to understand. It also adds another layer where the compiler can optimize asynchronous calls.
Specifically, in the above IRC example, now that everything is being awaited, even in a single-threaded process, multiple commands can now be processed simultaneously if they wait on external resources, since the listen! handler no longer blocks. If I were to implement the listen! loop myself, it would (a little simplified) look like:
async method listen(handle: Awaitable<Socket, String, Unit>)
loop
let line = await self.getline(MAX_LENGTH)
in
handle(self, line)
end
end
end
Note how the call to handle
is not awaited, thereby letting handlers execute concurrently (even in a single-threaded scenario, since the scheduler will yield while self.getline
is waiting on I/O). This is a really great pattern that allows for simple concurrency and efficient handling of IO bound work in a functional style (even if under the hood it's not very functional), and I think it'd be a great idea if it was included in Brick.
C# started it, ES6 has it, even C++ 14 has it. Async/await is an amazingly simple construct for creating asynchronous code. Weather it's implemented with promises or continuations on the back end, we'll see later (likely continuations, since I see no indication that Brick will be event-loop based).
Regardless, the async/await keyword syntax for defining asynchronous code is a godsend; it helps create self-documenting code, simplifies asynchronous control flow, and fits snugly with already-defined chunks of brick syntax:
Important notes on what I see as proper use:
async
isn't an used like an access modifier like in C++ or C#, instead, it's an alternate keyword for function declaration, which implies that the return type should be wrapped in anAwaitable
Promise/Future. This way, if manually specifying a type declaration for an async, you needn't include that yourself. In effect, theasync
keyword adds the type-> Awaitable<T>
to the end of the type line. You'll notice that for lambdas, the async keyword appears after the argument types. If I specifying the lambda's return type, it would appears before that. This makes sense, since in practice, the keyword modifies the return type of the function.As far as the specifics on how async/await interact with threading/blocking, the C# documentation section is excellent: http://msdn.microsoft.com/en-us/library/hh191443.aspx#BKMK_Threads