-
Notifications
You must be signed in to change notification settings - Fork 0
Advanced zhtw
English | 中文 | Русский | Español | Português | 繁體中文 | Deutsch
大師班:型別化智慧引用、呼叫原生 C 函式庫、記憶體管理、效能、將標註作為設計工具,以及一個完整的動手實作專案。
智慧引用是指向左值的型別化值。它以 權限 × 跟隨層 × 基礎型別 宣告:
&<permission> <follow> <base type> <name> = &<lvalue>;
-
權限(7 種):
r讀取、w寫入、m移動(指標)、rw、rm、wm、rwm。 -
跟隨層(4 種):
u程式層級(Unistream)、f方法層級、a作用域/區域層級、t執行緒層級。 -
基礎型別:
int/double/float/string/char/ 陣列 / 類別——通用。
合計 7 × 4 = 28 種引用型別。
int counter = 0;
&w u int wr = &counter; // writable program-level ref
Ref::write(wr, 10);
&r u int rr = &counter; // read-only ref
CIO::println(get Ref::read(rr)); // 10
&rw u int rw = &counter; // read-write
CIO::println(get rw); // 10
rw = 5;
CIO::println(counter); // 5
有了 m,引用就是可移動的指標(類似 C 的 a++):
ALL a = new int[3];
a[0] = 10; a[1] = 20; a[2] = 30;
&m u int mp = &a[1];
CIO::println(get mp); // 20
mp++;
CIO::println(get mp); // 30
mp = 99; // writes through the pointer
CIO::println(a[2]); // 99
CIO::println(cause Ref::move(mp)); // refused: pointer moved out of bounds
引用會拒絕其權限所禁止的操作——而拒絕原因本身就是一個值:
CIO::println(cause Ref::write(rr, 99));
// Ref refused: reference is read-only, cannot write
標註宣告串流與方法上的契約:
// A stream that must never be forked again:
Stream Sealed {
void ping();
} @unfork
Sealed BadFork {} // startup: refused: stream Sealed is @unfork, cannot fork
// A read-only stream: users may not call write methods:
Stream ReadOnly {
int count;
void bump();
int get();
}
ReadOnly RO {
void bump() { this::count = count + 1; } @write
int get() { res count; } @read
} @onlyread
- 方法上的
@write/@read明確宣告其讀寫性質——它們優先於 AST 啟發式判斷(看似唯讀的方法主體可以被宣告為寫入方法,反之亦然)。 -
@onlyread拒絕串流上任何寫入方法的呼叫。 -
@unfork拒絕所有派生路徑,包括對@unfork類別執行new。
串流可以綁定共享函式庫:
Stream m & "libm.so.6"; // bind libm
Main {
void exec() {
CIO::println(get m::sin(0)); // 0
CIO::println(get m::pow(2, 10)); // 1024
}
}
二進位函式以 double(*)(double, ...) 的形式呼叫(最多 6 個引數);匯出的符號會變成串流方法。bio_dlsym / 平台轉接層處理 dlopen/LoadLibrary 的差異,因此在 Windows 上也能運作。
- 直譯器使用區塊式記憶體池(arena)——配置的記憶體永遠不會移動。
- 預設上限:直譯模式 256 MiB;
0= 無限制。 - 上限旗標:
bio -e 256M script.bio(或-e 1G、-e 0)。 - 編譯產物:無上限,除非在環境中設定了
BIO_MEM_LIMIT;bio shell build會將此行為嵌入產生的 main 中。 - 達到上限時,程式會以明確的訊息停止:
memory limit exceeded (limit N bytes)。
-
快取:串流與方法在熱路徑上會被快取(
stream_cache/method_cache)——以相同名稱重複查詢的複雜度為 O(1)。 -
增量編譯:
bio build會對每個模組的原始碼進行雜湊;只有變更的模組會重新編譯(N module(s) cached, M recompiled)。 -
編譯模式:
bio shell build會將直譯器執行時期鏈結進獨立可執行檔——啟動瞬間完成,產物無需bio即可在任何地方執行。
make bin(經由 tools/make-dist.sh)使用 zig 為所有平台交叉編譯發行版目錄樹——不需要外部 SDK:
make bin
# bin/linux-x86_64/bin/bio + lib/libbio.so
# bin/win64/bin/bio.exe + lib/bio.dll + bio.bat
# bin/macos-arm64/bin/bio + lib/libbio.dylib
# ...平台:linux-x86_64、linux-arm64、win32、win64、win-arm64、macos-x86_64、macos-arm64。PATH 上需要 zig >= 0.14。
內部細節:啟動器以動態鏈結方式連結 lib/ 中的共享執行時期(rpath $ORIGIN/../lib);Windows 使用 bio.bat 設定 PATH。執行緒在 POSIX 上使用 ucontext、在 Windows 上使用 Win32 纖程;二進位函式庫透過平台轉接層使用 dlopen 或 LoadLibrary。
讓我們建置一個字詞頻率計數器——讀取檔案、統計字詞、印出排序報表。
bio init wordcountprogram main;
need function countWords; // provided by utils/counter.bio
Main {
void exec() {
if (CIO::getln() == "") { } // (placeholder for arg reading)
FIO::open("input.txt");
string text = FIO::readFile("input.txt");
ALL report = countWords(text);
CIO::println(get report);
}
}
program utils;
function countWords(text string) {
// SIO lets us scan word by word through a string buffer.
int words = 0;
for (int i = 0; i < text::length(); i = i + 1;) {
char c = text[i];
if (c == ' ' || c == '\n' || c == '\t') {
words = words + 1;
}
}
res words + 1; // last word has no trailing space
}
bio build . -s # standalone executable
bio build . -m # packaged .img with the platform runtime
bio run . # interpret directlybio build . -m wordcount.zip # one distributable file這就是完整的循環:原始碼 → 驗證過的套件 → 獨立二進位檔 → 跨平台套件。
-
bio --tokens file.bio— 傾印詞法分析器的記號串流。 - 拒絕訊息是一等公民:
cause expr會精確顯示請求失敗的原因。 - 以
make PROFILE=sanitize編譯,產生 ASan + UBSan 消毒版本。
- Home
- Beginner — first steps
- Intermediate — real usage
- Advanced — masterclass
- Build & Run
- Packaging
- Language-Reference
- BR-Model
- BTM-Model