#
Примеры использования Zig
Давайте рассмотрим простой пример "Hello World":
const std = @import("std");
pub fn main() !void {
const stdout = std.io.getStdOut().writer();
try stdout.print("Привет, мир!\n", .{});
}
Этот код выводит сообщение "Привет, мир!". Несмотря на простоту примера, видно, насколько лаконичен и выразителен синтаксис Zig.
#
Дополнения для версии Zig 0.15.1 и позже
Начиная с версии 0.15.1 подсистема ввода-вывода претерпела значительные изменения. Интерфейсы ввода-вывода стандартной библиотеки теперь используют буферизованный ввод-вывод по умолчанию. Это изменение сокращает количество дорогостоящих системных вызовов, но требует от разработчиков явного управления буферами и обязательного сброса вывода.
#
Пример: запись с помощью буфера
const std = @import("std");
pub fn main() !void {
var stdout_buffer: [1024]u8 = undefined;
var stdout_writer = std.fs.File.stdout().writer(&stdout_buffer);
const stdout = &stdout_writer.interface;
try stdout.print("Привет, мир!\n", .{});
// Требуется, чтобы вывод был передан в терминал
try stdout.flush();
}
Если не сделать заключительный stdout.flush, то в терминале ничего не появится.
Буферизованный ввод-вывод сокращает количество дорогостоящих системных вызовов ядра. Вместо того чтобы обращаться к ОС при каждом stdout.print, несколько операций записи объединяются в буфер и выполняются одновременно. Это значительно повышает эффективность ввода-вывода, особенно в приложениях, требовательных к производительности.
#
Небуферизованный вывод
Если вы хотите, чтобы данные записывались непосредственно в ОС без буферизации, передайте пустой срез (&.{}):
const std = @import("std");
pub fn main() !void {
var w = std.fs.File.stdout().writer(&.{});
const stdout = &w.interface;
try stdout.print("Привет, мир!\n", .{});
// В этом случае вызов .flush не требуется
}
Это позволяет обойти буферизацию, в ущерб эффективности. Используйте небуферизованные средства записи только в случае крайней необходимости, ибо буферизация почти всегда предпочтительнее.
Новый подход упрощает написание функций, принимающих любой объект типа Writer. Такая гибкость позволяет использовать один и тот же код для вывода в стандартный поток, файлы, сокеты или асинхронные потоки и т.п.