On branch main
modified: src/ch09.md new file: src/ex-ch09-08/build.zig new file: src/ex-ch09-08/calc/add.zig new file: src/ex-ch09-08/calc/build.zig new file: src/ex-ch09-08/calc/calc.zig new file: src/ex-ch09-08/program.zig
This commit is contained in:
132
src/ch09.md
132
src/ch09.md
@@ -686,10 +686,134 @@ test "dummy build test" {
|
||||
прошёл, как и должно было быть, поскольку `true != false`. Если вы
|
||||
подправите тест и снова запустите `zig build test`, то ничего не
|
||||
выведется, что и будет означать, что тест прошёл. По умолчанию система
|
||||
что либо выводит только в случае неудавшегося теста. Если нужно в любом
|
||||
случае что-то увидеть, используйте `zig build test --summary all`.
|
||||
|
||||
|
||||
тестов Zig что либо выводит только в случае неудавшегося теста. Если
|
||||
нужно в любом случае что-то увидеть, используйте `zig build test --summary all`.
|
||||
|
||||
В заключение отметим, что начинать проект можно (и, наверное, нужно) с
|
||||
выполнения `zig init-exe` или `zig init-lib` для запускаемых программ и
|
||||
библиотек, соответственно. Эти команды создадут надлежащий `build.zig`
|
||||
автоматически, причём хорошо документированный.
|
||||
|
||||
## Сторонние зависимости
|
||||
|
||||
Встроенный в Zig менеджер пакетов пока ещё относительно новый и, как
|
||||
следствие, несколько недоработан. Тем не менее, его вполне можно
|
||||
использовать в том виде, какой он есть на данный момент. Далее мы
|
||||
рассмотрим два вопроса, создание пакетов и использование пакетов.
|
||||
|
||||
Сначала создадим каталог `calc` и в нём три файла, первый из которых
|
||||
назовём `add.zig`, вот его содержимое:
|
||||
|
||||
```zig
|
||||
// Oh, a hidden lesson, look at the type of b
|
||||
// and the return type!!
|
||||
|
||||
pub fn add(a: anytype, b: @TypeOf(a)) @TypeOf(a) {
|
||||
return a + b;
|
||||
}
|
||||
|
||||
const testing = @import("std").testing;
|
||||
test "add" {
|
||||
try testing.expectEqual(@as(i32, 32), add(30, 2));
|
||||
}
|
||||
```
|
||||
|
||||
Конечно, делать пакет ради сложения двух чисел это глуповато,
|
||||
но такая предельная простота позволит нам сосредоточиться
|
||||
исключительно на вещах, связанных с пакетами, а не на функциональности пакетов.
|
||||
Второй файл, который мы добавим (`calc.zig`) будет такой же простяцкий:
|
||||
|
||||
```zig
|
||||
pub const add = @import("add.zig").add;
|
||||
|
||||
test {
|
||||
// By default, only tests in the specified file
|
||||
// are included. This magic line of code will
|
||||
// cause a reference to all nested containers
|
||||
// to be tested.
|
||||
@import("std").testing.refAllDecls(@This());
|
||||
}
|
||||
```
|
||||
|
||||
Мы разместили эти два кусочка кода в разных файлах
|
||||
для того, чтобы `zig build` автоматически собрал
|
||||
и "упаковал" все файлы нашего проекта. Добавляем `build.zig`:
|
||||
|
||||
```zig
|
||||
const std = @import("std");
|
||||
|
||||
pub fn build(b: *std.Build) !void {
|
||||
const target = b.standardTargetOptions(.{});
|
||||
const optimize = b.standardOptimizeOption(.{});
|
||||
|
||||
const tests = b.addTest(.{
|
||||
.target = target,
|
||||
.optimize = optimize,
|
||||
.root_source_file = .{ .path = "calc.zig" },
|
||||
});
|
||||
|
||||
const test_cmd = b.addRunArtifact(tests);
|
||||
test_cmd.step.dependOn(b.getInstallStep());
|
||||
const test_step = b.step("test", "Run the tests");
|
||||
test_step.dependOn(&test_cmd.step);
|
||||
}
|
||||
```
|
||||
|
||||
Всё это повторение того, что мы уже видели в предыдущем разделе.
|
||||
В частности, имея эти три файла, уже можно запустить `zig build test --summary all`:
|
||||
|
||||
```
|
||||
Build Summary: 4/4 steps succeeded; 2/2 tests passed
|
||||
test success
|
||||
└─ run test 2 passed 1ms MaxRSS:1M
|
||||
├─ zig test Debug native success 2s MaxRSS:185M
|
||||
└─ install cached
|
||||
```
|
||||
|
||||
Вернёмся теперь к примеру из предыдущего раздела и к файлу
|
||||
`build.zig`, который мы там сделали. Начнём с добавления
|
||||
в него нашего локального `calc` в качестве зависимости,
|
||||
для чего нужно 3 дополнения. Сначала создадим модуль,
|
||||
указывающий на `calc`:
|
||||
|
||||
```zig
|
||||
// You can put this near the top of the build
|
||||
// function, before the call to addExecutable.
|
||||
|
||||
const calc_module = b.addModule("calc", .{
|
||||
.source_file = .{ .path = "PATH_TO_CALC_PROJECT/calc.zig" },
|
||||
});
|
||||
```
|
||||
|
||||
Теперь нужно добавить этот модуль к переменным `exe` и `tests`:
|
||||
|
||||
```zig
|
||||
const exe = b.addExecutable(.{
|
||||
.name = "learning",
|
||||
.target = target,
|
||||
.optimize = optimize,
|
||||
.root_source_file = .{ .path = "learning.zig" },
|
||||
});
|
||||
// add this
|
||||
exe.addModule("calc", calc_module);
|
||||
b.installArtifact(exe);
|
||||
|
||||
....
|
||||
|
||||
const tests = b.addTest(.{
|
||||
.target = target,
|
||||
.optimize = optimize,
|
||||
.root_source_file = .{ .path = "learning.zig" },
|
||||
});
|
||||
// add this
|
||||
tests.addModule("calc", calc_module);
|
||||
```
|
||||
|
||||
Теперь в вашем проекте можно импортировать модуль:
|
||||
|
||||
```zig
|
||||
const calc = @import("calc");
|
||||
...
|
||||
calc.add(1, 2);
|
||||
```
|
||||
|
||||
|
||||
40
src/ex-ch09-08/build.zig
Normal file
40
src/ex-ch09-08/build.zig
Normal file
@@ -0,0 +1,40 @@
|
||||
|
||||
const std = @import("std");
|
||||
|
||||
pub fn build(b: *std.Build) !void {
|
||||
const target = b.standardTargetOptions(.{});
|
||||
const optimize = b.standardOptimizeOption(.{});
|
||||
|
||||
const calc_module = b.addModule("calc", .{
|
||||
.source_file = .{ .path = "calc/calc.zig" },
|
||||
});
|
||||
|
||||
// setup executable
|
||||
const exe = b.addExecutable(.{
|
||||
.name = "program",
|
||||
.target = target,
|
||||
.optimize = optimize,
|
||||
.root_source_file = .{ .path = "program.zig" },
|
||||
});
|
||||
exe.addModule("calc", calc_module);
|
||||
b.installArtifact(exe);
|
||||
|
||||
// run step
|
||||
const run_cmd = b.addRunArtifact(exe);
|
||||
run_cmd.step.dependOn(b.getInstallStep());
|
||||
const run_step = b.step("run", "test run");
|
||||
run_step.dependOn(&run_cmd.step);
|
||||
|
||||
// test step
|
||||
const tests = b.addTest(.{
|
||||
.target = target,
|
||||
.optimize = optimize,
|
||||
.root_source_file = .{ .path = "program.zig" },
|
||||
});
|
||||
tests.addModule("calc", calc_module);
|
||||
|
||||
const test_cmd = b.addRunArtifact(tests);
|
||||
test_cmd.step.dependOn(b.getInstallStep());
|
||||
const test_step = b.step("test", "Run the tests");
|
||||
test_step.dependOn(&test_cmd.step);
|
||||
}
|
||||
12
src/ex-ch09-08/calc/add.zig
Normal file
12
src/ex-ch09-08/calc/add.zig
Normal file
@@ -0,0 +1,12 @@
|
||||
|
||||
// Oh, a hidden lesson, look at the type of b
|
||||
// and the return type!!
|
||||
|
||||
pub fn add(a: anytype, b: @TypeOf(a)) @TypeOf(a) {
|
||||
return a + b;
|
||||
}
|
||||
|
||||
const testing = @import("std").testing;
|
||||
test "add" {
|
||||
try testing.expectEqual(@as(i32, 32), add(30, 2));
|
||||
}
|
||||
17
src/ex-ch09-08/calc/build.zig
Normal file
17
src/ex-ch09-08/calc/build.zig
Normal file
@@ -0,0 +1,17 @@
|
||||
const std = @import("std");
|
||||
|
||||
pub fn build(b: *std.Build) !void {
|
||||
const target = b.standardTargetOptions(.{});
|
||||
const optimize = b.standardOptimizeOption(.{});
|
||||
|
||||
const tests = b.addTest(.{
|
||||
.target = target,
|
||||
.optimize = optimize,
|
||||
.root_source_file = .{ .path = "calc.zig" },
|
||||
});
|
||||
|
||||
const test_cmd = b.addRunArtifact(tests);
|
||||
test_cmd.step.dependOn(b.getInstallStep());
|
||||
const test_step = b.step("test", "Run the tests");
|
||||
test_step.dependOn(&test_cmd.step);
|
||||
}
|
||||
9
src/ex-ch09-08/calc/calc.zig
Normal file
9
src/ex-ch09-08/calc/calc.zig
Normal file
@@ -0,0 +1,9 @@
|
||||
pub const add = @import("add.zig").add;
|
||||
|
||||
test {
|
||||
// By default, only tests in the specified file
|
||||
// are included. This magic line of code will
|
||||
// cause a reference to all nested containers
|
||||
// to be tested.
|
||||
@import("std").testing.refAllDecls(@This());
|
||||
}
|
||||
16
src/ex-ch09-08/program.zig
Normal file
16
src/ex-ch09-08/program.zig
Normal file
@@ -0,0 +1,16 @@
|
||||
|
||||
const std = @import("std");
|
||||
const calc = @import("calc");
|
||||
|
||||
pub fn main() void {
|
||||
const a: u32 = 3;
|
||||
const b: u32 = 4;
|
||||
const c: u32 = calc.add(a, b);
|
||||
std.debug.print("{} + {} = {}\n", .{a, b, c});
|
||||
}
|
||||
|
||||
test "calc.add() test" {
|
||||
const a: u32 = 3;
|
||||
const b: u32 = 4;
|
||||
try std.testing.expectEqual(calc.add(a, b), 8); // will fail
|
||||
}
|
||||
Reference in New Issue
Block a user