24 ms·
Go doesn't need "coloring bloat", but you can still handle the need to run code on a specific thread using LockOSThread.[0] If you absolutely need your code tha
by coder543 5y ago
Go doesn't need "coloring bloat", but you can still handle the need to run code on a specific thread using LockOSThread.[0] If you absolutely need your code that interacts with the OS GUI functions to be running on the first thread the OS spawned, the documentation even tells you how to do that.
This is an exceptionally low level detail that very few people should ever have to think about. Is there something else you can point to that's pertinent to more developers?
Having written Go for years (as well as a good bit of Rust), I love not having to worry about async/await being the concurrency model, and thread identity is never something I think about. With the upcoming Go release that brings generics, I think there are some code patterns that inherently benefit from an async/await style pattern where you spawn several tasks and await their results, so I'm looking forward to having a generic pattern to spawn goroutines that return a value into a Promise... but the infectious nature of "real" async/await is not something I would consider beneficial in most languages. Rust is a language that is all about low level details and performance, so it actually makes sense there, but that's a rare exception, in my opinion.
Developers generally shouldn't need to worry about things a good runtime can take care of, just like you don't need to worry about when you're going to free an object in C#... the runtime takes care of these details that are rarely relevant to meeting the developer's objectives. When you absolutely need that control, there are usually escape hatches. If the application you're writing frequently requires unlimited control, you should probably be using an unmanaged language like Rust to begin with.
[0]: https://pkg.go.dev/runtime#LockOSThread https://pkg.go.dev/runtime#LockOSThread
- jayd16 5y ago>This is an exceptionally low level detail that very few people should ever have to think about. Every popular UI package uses a UI thread pattern. Every UI dev thinks about this.
- coder543 5y agoThis should be handled transparently by the library, not the application developer. Which is not to say that UI frameworks developed decades ago got this right. As I said, Go handles this problem just fine, apparently disproving your original argument, which was the main point. Async/await with explicit yield points isn’t needed to support this pattern.
- jayd16 5y agoAs soon as anyone gets it right then perhaps async/await will be the wrong choice but not until then. My understanding is Go UIs are mostly using html or some other languages/frameworks for UI work. Can you link me to a popular native Golang GUI framework to look at?
- coder543 5y agoThere are definitely libraries, such as bindings to GTK: https://github.com/gotk3/gotk3 https://github.com/gotk3/gotk3 or Win32: https://github.com/rodrigocfd/windigo https://github.com/rodrigocfd/windigo The point remains that it is possible to do these things without async/await, which you seemingly asserted it was not. Everything else is irrelevant, as far as I can tell. Go absolutely isn’t frequently used to develop native UIs, so of course “popular” is a strange thing to discuss here. Why isn’t it popular? Most likely because the kind of visual UI builder tools used in Visual Studio or Android Studio have never had an equivalent funded for use with Go, due to lack of commercial support for that use case. Beyond that, web UI frameworks are immensely popular these days, and most companies would rather use those, further removing motivation to really “make native GUI happen” in Go, but there are niche use cases out there, as evidenced by the existence of libraries. If Go had come out in the early 2000s, native GUI support would likely have been a much higher priority. This is pretty far off topic, though.
- jayd16 5y ago>The point remains that it is possible to do these things without async/await My point was simply that async/await is good and useful when you're dealing with main threads. You asserted that that was a niche use case and UI programming should not think about thread, to which I replied that it was exceedingly common. The frameworks you link to do indeed use the main thread pattern which can be blocked by callbacks into Go. You need to be aware of what code you run on the main thread even in the Go code. The problem is naturally colored. Async/await is useful in dealing with that.
- 5y ago
- hackerfromthefu 5y agoOne of the really interesting things about C# is the breadth of the language, it handles close to if not every possible kind of program that can be written, and that's by design. In other words it's a fully capable systems level language as well as an application language. There are a number of design choices that people use to writing high level applications think are funny but when you reflect on them they are there to allow low level control for systems level or high performance programming. I used to be baffled by some of the designs until I realised that it's a language for everyone/every system, not just for what I personally am doing right now.
- coder543 5y agoI think a more compelling argument would be that C# pioneered a lot of things we take for granted, and it’s impressive how much they’ve been able to change the language over time to keep it relevant as the state of the art advanced, but supporting the legacy of the language requires some tradeoffs. I agree it is a very capable language, but not every aspect is perfect. I would generally prefer C# over a lot of the alternatives.
- int_19h 5y agoC# can call into WinRT async APIs as naturally as ones written in C#. How does Go handle this scenario?
- pjmlp 5y agoKind of, only true when speaking about .NET Native, now with standard .NET + CsWinRT it isn't as natural as it used to be. More an exercise in patience dealing with the WinRT mess.
- coder543 5y agoMy discussion was intended to be about two things: - is function coloring better than alternatives? - is it possible to interact with APIs that require they be called from a specific UI thread using those alternatives? The answers are resoundingly “no” and “yes”. The point is that I think C# should at some point adopt lightweight preemptible threads similar to goroutines for the benefits, not that you need to switch to Go for GUI apps on Windows. I don’t agree at all that function coloring for async is a benefit, or that poorly written tasks being able to block the executor is a benefit, which is what the GP basically argued. C# is a good language, but defending function coloring feels the same as those Go developers who defended not having generics for years. It’s important to be able to recognize the shortcomings in languages so that improvements can be made. Generics will be a benefit to the Go language, even if it took a surprisingly long time to materialize. Async in C# is better than what it had before, but that doesn’t mean it is perfect. To your question more directly, Go’s runtime automatically uses the underlying native async APIs in most places where it makes sense in the standard library. WinRT probably isn’t used by Go, but I haven’t ever looked. If you’re specifically referring to UI APIs, then this is irrelevant to the discussion, because I’m not saying you should switch to Go for that. Plus, Google doesn’t care about using native windows GUI APIs from Go, so it probably wouldn’t fit your definition of “natural”, since I doubt anyone has put in the effort to clear that bar.
- int_19h 5y agoFunction coloring is what allows WinRT to be a language-agnostic async API (whether we're talking about UI or not is immaterial - it's all async). I'm well aware of the shortcomings of coloring, but the point remains that it's the only way to do async that does not result in insular ecosystems with a penchant to rewrite everything so as to gain the benefits of their bespoke green threading (i.e. exactly like Go). This may change if we can even standardize green threads on OS level, such that all languages can target it in an interoperable way. But the experience with the adoption (or rather lack thereof) of fibers in Win32 shows just how difficult this can be.