Skip to content
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: add sync.Future #17483

Closed
funny-falcon opened this issue Oct 17, 2016 · 6 comments
Closed

Proposal: add sync.Future #17483

funny-falcon opened this issue Oct 17, 2016 · 6 comments

Comments

@funny-falcon
Copy link
Contributor

funny-falcon commented Oct 17, 2016

"future" is well known useful concurrency primitive.
So it strangely missed from language and standard library.
Since #17466 (add to language) doubtfully will be accepted, may be it is possible to add it to stdlib.

Proposal

add sync.Future with following properties:

  • it should provide method for getting wait channel to be used in select statement,
  • it should guarantee value is set only once even when concurrent goroutines tries to set it simultaneously,
  • it may have convinient method for waiting for "completion" and getting value at once
    As additional properties:
  • it may have separate field for storing error,
  • then method for getting value will return both value and error,

As example implementation (but not final) I suggest following:
https://github.com/funny-falcon/go-datastructures/blob/future_selectable_lazy_chan/futures/selectable.go
Pros:

  • fast check in GetResult on already filled future,
  • wait channel is lazy created,
  • on Fill, pointer to channel is changed to single global closed chan, so per Future channel could be early collected by GC (or even not allocated at all)
@RLH
Copy link
Contributor

RLH commented Oct 17, 2016

It seems that all of this can be implemented as an independent library
without any change to sync. The separate library approach would avoid the
cost of increasing the api surface of sync. Furthermore experience with the
library could inform a better design and allow the evolution of the API in
ways that putting it into sync would preclude.

It is not immediately obvious how one would implement "early collected by
GC" in Go's current implementation.

On Mon, Oct 17, 2016 at 1:04 PM, Sokolov Yura notifications@github.com
wrote:

"future" is well known useful concurrency primitive.
So it strangely missed from language and standard library.
Since #17466 #17466 (add to
language) doubtfully will be accepted, may be it is possible to add it to
stdlib.
Proposal

add sync.Future with following properties:

  • it should provide method for getting wait channel to be used in
    select statement,
  • it should guarantee value is set only once even when concurrent
    goroutines tries to set it simultaneously,
  • it may have convinient method for waiting for "completion" and
    getting value at once As additional properties:
  • it may have separate field for storing error,
  • then method for getting value will return both value and error,

As example implementation (but not final) I suggest following:
https://github.com/Workiva/go-datastructures/blob/master/
futures/selectable.go
Pros:

  • fast check in GetResult on already filled future,
  • on Fill, pointer to channel is changed to single global closed chan,
    so per Future channel could be early collected by GC. Cons:
  • it is allocated using constructor. I think, it could be fixed with
    some additional checks in wchan and Fill methods (probably, then
    allocation of chan could be omitted of fastly resolved futures)


You are receiving this because you are subscribed to this thread.
Reply to this email directly, view it on GitHub
#17483, or mute the thread
https://github.com/notifications/unsubscribe-auth/AA7Wn21Nny7H_tfcsxq2dYEI_PUNTl5mks5q06qPgaJpZM4KY3Zb
.

@quentinmit quentinmit added this to the Proposal milestone Oct 17, 2016
@OneOfOne
Copy link
Contributor

Reading the original proposal, honestly you made no valid arguments on why this should even be a thing.

Less than 20 LOCs and does the job just fine, https://play.golang.org/p/PmMEGXaawH

@funny-falcon
Copy link
Contributor Author

@OneOfOne neither your "future" could be used in select statement, nor it could be used without producing new goroutine.
Your example doesn't satisfy proposal requirements.

@funny-falcon
Copy link
Contributor Author

That is why it should be a thing:

  • there is a lot of way to implement it wrong way,
  • there is a lot of ways to correctly implement subset of requirements,
  • there is a lot of ways to implement it inefficiently,
  • but few ways to implement correctly all requirements in efficient way.

I thought "future" is very convenient concurrent primitive.
I used it many times to solve complex problems in an easy way.
But looks like, community simply doesn't bother.
Looks like very few people face same problems.
So most of people just doesn't understand, what are futures for, and why it is good to have its reliable implementation.
It's a pity.

Should I close this proposal? (I cannot close #17466 cause it is locked)

@ianlancetaylor
Copy link
Member

As a general rule, as @RLH said above, the way to start something like this is to write an external library. If that seems to work well we can consider adopting it in the Go standard library.

I'm going to close this proposal for now, but feel free to ping it again if you have an external library that people are adopting.

@funny-falcon
Copy link
Contributor Author

What about #17466 ? Looks like it also has no chances.

@golang golang locked and limited conversation to collaborators Oct 19, 2017
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

6 participants