Added RingBuffer

This commit is contained in:
abux 2026-07-13 16:41:14 +01:00
parent b87f315b57
commit 7e1f1c5e4a
2 changed files with 104 additions and 0 deletions

View file

@ -13,6 +13,7 @@ pub const ansi = @import("ansi.zig");
pub const Handle = @import("handle.zig").Handle; pub const Handle = @import("handle.zig").Handle;
pub const SlotMap = @import("slot_map.zig").SlotMap; pub const SlotMap = @import("slot_map.zig").SlotMap;
pub const KeyedSlotMap = @import("keyed_slot_map.zig").KeyedSlotMap; pub const KeyedSlotMap = @import("keyed_slot_map.zig").KeyedSlotMap;
pub const RingBuffer = @import("ring_buffer.zig").RingBuffer;
pub const TypeID = @import("type_id.zig").of; pub const TypeID = @import("type_id.zig").of;
// //
@ -126,4 +127,16 @@ test "SlotMap" {
log.debug("...", .{}); log.debug("...", .{});
log.trace("...", .{}); log.trace("...", .{});
} }
var ring: RingBuffer([]const u8, 3) = .{};
try ring.push("Hello");
try ring.push("World");
try ring.push("!");
var i: usize = 0;
while (ring.pop()) |data| {
i += 1;
std.debug.print("ring[{}] = \"{s}\"\n", .{ i, data });
}
} }

91
src/ring_buffer.zig Normal file
View file

@ -0,0 +1,91 @@
const std = @import("std");
/// ----------------------------------------------------
/// ----------------------------------------------------
pub fn RingBuffer(
comptime T: type,
comptime Capacity: usize,
) type {
return struct {
const Self = @This();
//
// FIELDS
//
buffers: [Capacity]T = std.mem.zeroes([Capacity]T),
head: usize = 0,
tail: usize = 0,
count: usize = 0,
/// ----------------------------------------------------
/// ----------------------------------------------------
pub fn isEmpty(self: *const Self) bool {
return self.count == 0;
}
/// ----------------------------------------------------
/// ----------------------------------------------------
pub fn isFull(self: *const Self) bool {
return self.count == Capacity;
}
/// ----------------------------------------------------
/// ----------------------------------------------------
pub fn push(self: *Self, value: T) error{Full}!void {
if (self.isFull()) return error.Full;
self.buffers[self.tail] = value;
self.tail = (self.tail + 1) % Capacity;
self.count += 1;
}
/// ----------------------------------------------------
/// ----------------------------------------------------
pub fn pushOverwrite(self: *Self, value: T) void {
if (self.isFull()) {
self.head = (self.head + 1) % Capacity;
} else {
self.count += 1;
}
self.buffers[self.tail] = value;
self.tail = (self.tail + 1) % Capacity;
}
/// ----------------------------------------------------
/// ----------------------------------------------------
pub fn pop(self: *Self) ?T {
if (self.isEmpty()) return null;
const item = self.buffers[self.head];
self.head = (self.head + 1) % Capacity;
self.count -= 1;
return item;
}
/// ----------------------------------------------------
/// ----------------------------------------------------
pub fn peek(self: *const Self) ?T {
if (self.isEmpty()) return null;
return self.buffers[self.head];
}
/// ----------------------------------------------------
/// ----------------------------------------------------
pub fn at(self: *const Self, index: usize) ?T {
if (index >= self.count) return null;
return self.buffers[(self.head + index) % Capacity];
}
/// ----------------------------------------------------
/// ----------------------------------------------------
pub fn len(self: *const Self) usize {
return self.count;
}
/// ----------------------------------------------------
/// ----------------------------------------------------
pub fn capacity(_: *const Self) usize {
return Capacity;
}
};
}