Go Programming Fundamentals · Concurrency & Idiomatic Go
Goroutines and Channels
Run concurrent work and communicate safely
Goroutines and Channels
A goroutine is a lightweight thread managed by the Go runtime. Starting one is as simple as prefixing a function call with the go keyword.
go processTask(taskID)
Channels
Channels let goroutines communicate and synchronize without shared-memory locking. Sending and receiving block until both sides are ready, which naturally coordinates work.
ch := make(chan string)
go func() {
ch <- "done"
}()
msg := <-ch
Select
The select statement waits on multiple channel operations at once, enabling patterns like timeouts and fan-in/fan-out pipelines.
Practice questions
What is a goroutine, and how expensive is it compared to an OS thread?
Answer
Summary
A goroutine is a lightweight, runtime-managed unit of concurrent execution — far cheaper than an OS thread, so a program can comfortably run thousands of them at once.
Longer Answer
A goroutine is a lightweight, runtime-managed unit of concurrent execution — far cheaper than an OS thread, so a program can comfortably run thousands of them at once. This low overhead is exactly why goroutines are used so liberally in idiomatic Go code, unlike threads in many other languages. In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview.
Key Points
- A goroutine is a lightweight, runtime-managed unit of concurrent execution — far cheaper than an OS thread, so a program can comfortably run thousands of them at once
- This low overhead is exactly why goroutines are used so liberally in idiomatic Go code, unlike threads in many other languages
- In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview
- Use the answer to connect the concept back to a realistic production or interview scenario for 'What is a goroutine, and how expensive is it compared to an OS thread?'
Comparison / Tradeoffs
| Aspect | Notes |
|---|---|
| Core idea | A goroutine is a lightweight, runtime-managed unit of concurrent execution — far cheaper than an OS thread, so a program can comfortably run thousands of them at once. |
| Practical tradeoff | This low overhead is exactly why goroutines are used so liberally in idiomatic Go code, unlike threads in many other languages. |
Why
Summary
This low overhead is exactly why goroutines are used so liberally in idiomatic Go code, unlike threads in many other languages.
Longer Answer
This low overhead is exactly why goroutines are used so liberally in idiomatic Go code, unlike threads in many other languages. In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview.
Key Points
- This low overhead is exactly why goroutines are used so liberally in idiomatic Go code, unlike threads in many other languages
- In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview
- In an interview, relate 'What is a goroutine, and how expensive is it compared to an OS thread?' to implementation decisions, tradeoffs, and operational impact
- Use the answer to connect the concept back to a realistic production or interview scenario for 'What is a goroutine, and how expensive is it compared to an OS thread?'
Comparison / Tradeoffs
| Aspect | Notes |
|---|---|
| Core idea | This low overhead is exactly why goroutines are used so liberally in idiomatic Go code, unlike threads in many other languages. |
| Practical tradeoff | In an interview, relate 'What is a goroutine, and how expensive is it compared to an OS thread?' to implementation decisions, tradeoffs, and operational impact. |
Why do channel sends and receives block by default, and why is that useful?
Answer
Summary
An unbuffered channel blocks until both a sender and receiver are ready, which naturally synchronizes two goroutines without needing separate locks.
Longer Answer
An unbuffered channel blocks until both a sender and receiver are ready, which naturally synchronizes two goroutines without needing separate locks. This is Go's philosophy in practice: 'don't communicate by sharing memory; share memory by communicating' — channels replace explicit locks for many use cases. In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview.
Key Points
- An unbuffered channel blocks until both a sender and receiver are ready, which naturally synchronizes two goroutines without needing separate locks
- This is Go's philosophy in practice: 'don't communicate by sharing memory; share memory by communicating' — channels replace explicit locks for many use cases
- In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview
- Use the answer to connect the concept back to a realistic production or interview scenario for 'Why do channel sends and receives block by default, and why is that useful?'
Comparison / Tradeoffs
| Aspect | Notes |
|---|---|
| Core idea | An unbuffered channel blocks until both a sender and receiver are ready, which naturally synchronizes two goroutines without needing separate locks. |
| Practical tradeoff | This is Go's philosophy in practice: 'don't communicate by sharing memory; share memory by communicating' — channels replace explicit locks for many use cases. |
Why
Summary
This is Go's philosophy in practice: 'don't communicate by sharing memory; share memory by communicating' — channels replace explicit locks for many use cases.
Longer Answer
This is Go's philosophy in practice: 'don't communicate by sharing memory; share memory by communicating' — channels replace explicit locks for many use cases. In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview.
Key Points
- This is Go's philosophy in practice: 'don't communicate by sharing memory; share memory by communicating' — channels replace explicit locks for many use cases
- In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview
- In an interview, relate 'Why do channel sends and receives block by default, and why is that useful?' to implementation decisions, tradeoffs, and operational impact
- Use the answer to connect the concept back to a realistic production or interview scenario for 'Why do channel sends and receives block by default, and why is that useful?'
Comparison / Tradeoffs
| Aspect | Notes |
|---|---|
| Core idea | This is Go's philosophy in practice: 'don't communicate by sharing memory; share memory by communicating' — channels replace explicit locks for many use cases. |
| Practical tradeoff | In an interview, relate 'Why do channel sends and receives block by default, and why is that useful?' to implementation decisions, tradeoffs, and operational impact. |
What problem does the `select` statement solve?
Answer
Summary
It lets a goroutine wait on multiple channel operations at once and proceeds with whichever one becomes ready first, which is what you need for patterns like timeouts or merging multiple input streams.
Longer Answer
It lets a goroutine wait on multiple channel operations at once and proceeds with whichever one becomes ready first, which is what you need for patterns like timeouts or merging multiple input streams. select is essential for anything beyond the simplest single-channel handoff — timeouts, fan-in, and cancellation all rely on it. In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview.
Key Points
- It lets a goroutine wait on multiple channel operations at once and proceeds with whichever one becomes ready first, which is what you need for patterns like timeouts or merging multiple input streams
- select is essential for anything beyond the simplest single-channel handoff — timeouts, fan-in, and cancellation all rely on it
- In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview
- Use the answer to connect the concept back to a realistic production or interview scenario for 'What problem does the
selectstatement solve?'
Comparison / Tradeoffs
| Aspect | Notes |
|---|---|
| Core idea | It lets a goroutine wait on multiple channel operations at once and proceeds with whichever one becomes ready first, which is what you need for patterns like timeouts or merging multiple input streams. |
| Practical tradeoff | select is essential for anything beyond the simplest single-channel handoff — timeouts, fan-in, and cancellation all rely on it. |
Why
Summary
select is essential for anything beyond the simplest single-channel handoff — timeouts, fan-in, and cancellation all rely on it.
Longer Answer
select is essential for anything beyond the simplest single-channel handoff — timeouts, fan-in, and cancellation all rely on it. In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview.
Key Points
- select is essential for anything beyond the simplest single-channel handoff — timeouts, fan-in, and cancellation all rely on it
- In practice, explain where this shows up in production code, what tradeoffs matter, and how you would justify the choice in an interview
- In an interview, relate 'What problem does the
selectstatement solve?' to implementation decisions, tradeoffs, and operational impact - Use the answer to connect the concept back to a realistic production or interview scenario for 'What problem does the
selectstatement solve?'
Comparison / Tradeoffs
| Aspect | Notes |
|---|---|
| Core idea | select is essential for anything beyond the simplest single-channel handoff — timeouts, fan-in, and cancellation all rely on it. |
| Practical tradeoff | In an interview, relate 'What problem does the select statement solve?' to implementation decisions, tradeoffs, and operational impact. |
Open in the app to mark lessons complete, take notes and track your progress.