-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathex03_queue.go
More file actions
49 lines (40 loc) · 1.45 KB
/
ex03_queue.go
File metadata and controls
49 lines (40 loc) · 1.45 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
package channels
// Context: Bounded Buffering & Deadlocks
// You are designing an ingestion queue. External networks dump logs into this queue.
// An internal processing engine reads them off.
//
// Why this matters: If the queue is unbuffered (`make(chan string)`), the ingestion
// network instantly blocks if the processor is busy, causing timeouts to clients.
// If the queue has infinite capacity (not possible natively, but via wrappers),
// a slow processor will cause an Out-Of-Memory panic.
// An idiomatic Go bounded queue is simply a buffered channel: (`make(chan string, 100)`).
//
// Requirements:
// 1. Refactor `NewQueue` to create a buffered channel of size `capacity`.
// 2. Implement `Enqueue` so it DOES NOT block indefinitely. Use a `select` statement.
// - If the channel is full, immediately return `ErrQueueFull`.
// 3. Implement `Dequeue` to pull an item.
import (
"errors"
)
var ErrQueueFull = errors.New("queue is full")
type LogQueue struct {
// TODO: Define the buffered channel
stream chan string
}
func NewQueue(capacity int) *LogQueue {
// BUG: Unbuffered channel
return &LogQueue{
stream: make(chan string),
}
}
func (q *LogQueue) Enqueue(logMsg string) error {
// BUG: This blocks forever if the processor is busy.
// TODO: Use select with a default case to drop the message if the buffer is full!
q.stream <- logMsg
return nil
}
func (q *LogQueue) Dequeue() string {
// Blocks until a log is available
return <-q.stream
}