如果你会 Python 或 C,十分钟就能写出第一段 HP。从安装到所有权,循序渐进。If you know Python or C, you'll write HP in ten minutes. From install to ownership, step by step.
下载 hpc(内置 LLVM 后端与 LLD 链接器)并加入 PATH。HP 没有运行时:hpc 默认 -O2,直接产出原生可执行文件。Download hpc (bundles the LLVM backend and LLD) and add it to PATH. HP has no runtime: hpc defaults to -O2 and emits a native executable.
hpc hello.hp # 默认 -O2,生成 hello.hp 同目录的 hello.exe
hpc -O3 --lto hello.hp # 极致速度 + 跨模块链接期优化
./hello.exe程序从 main() 开始执行。用 module { "<std.io>" } 解锁内置 I/O(类比 C 的 #include <stdio.h>),随后用 std.io.print 输出。# 是注释;缩进与大括号都可划分代码块,两者等价。Execution starts at main(). module { "<std.io>" } unlocks built-in I/O (like C's #include <stdio.h>), then std.io.print outputs. # comments the line; indentation or braces define blocks — both are equivalent.
module { "<std.io>" }
# 单行注释
## 多行注释
这里随便写,用 ## 结束
##
fn main() {
std.io.print("Hello, HP!")
}num 是编译期数值别名,整数解析为原生字长,浮点解析为 f64;要精确宽度就用 i8…i64、f32、f64。字符串用 " 或 '。num is a compile-time numeric alias (int → native word, float → f64); use i32, f64… for exact widths. Strings use " or '.
module { "<std.io>" }
a = 10 # int(底层 i64)
pi: f64 = 3.1415 # 显式类型注解
name = "HP"
c = a + pi * 2 # 混合运算,编译期提升为 float
msg = f"你好,{name}! sum = {c}"
std.io.print(msg)
to_int: i32 = i32(pi) # 显式截断转换
is_ready: bool = true # bool 真假
std.io.print(to_int)零运行时:f-string 在编译期展开为字符串拼接,运行时零格式化开销;int→float 扩宽自动进行,float→int 必须显式转换。Zero-runtime: f-strings expand to string concatenation at compile time — zero formatting cost; int→float widens automatically, float→int must be explicit.
if / elif / else、for 与 while 和 Python 类似;break / continue 语义一致。遍历已知类型时编译器会特化成原生循环,性能与手写 C 相当。if / elif / else, for and while feel like Python; break / continue work the same. Iterating known types specializes to native loops — C-level performance.
module { "<std.io>" }
for i in range(1, 7):
if i % 2 == 0:
std.io.print(f"{i} 是偶数")
else:
std.io.print(f"{i} 是奇数")
n = 0
while n < 3:
std.io.print(n)
n += 1用 fn 定义函数;返回类型用 -> 或 : 皆可,两者等价。默认参数必须是编译期常量。尾递归会自动编译为 goto,零栈帧增长。Define functions with fn; the return type accepts -> or :. Default args must be compile-time constants. Tail recursion compiles to goto — no stack growth.
module { "<std.io>" }
fn greet(name: str, prefix: str = "Hi") -> str {
return f"{prefix}, {name}"
}
fn factorial(n) {
if n <= 1:
return 1
return n * factorial(n - 1)
}
std.io.print(greet("HP"))
std.io.print(factorial(5)) # 120匿名函数用 fn(参数){...} 直接作表达式,是 map / filter 与高阶函数的绝配。它们能捕获外部变量形成闭包。Use fn(参数){...} as an inline expression — ideal for map / filter and higher-order functions. They can capture outer variables to form closures.
module { "<std.io>" }
double = fn(x) { return x * 2 }
std.io.print(double(21)) # 42
fn apply(func, value) { return func(value) }
std.io.print(apply(fn(x) { return x * 3 }, 10)) # 30
fn make_adder(base) {
return fn(x) { return x + base } # 闭包捕获 base
}
add10 = make_adder(10)
std.io.print(add10(5)) # 15用 struct 定义值类型,impl 添加方法。字段按关键字参数实例化,编译器自动重排消除 padding,零开销访问。Define value types with struct and attach methods with impl. Instantiate by keyword, and the compiler reorders fields to kill padding — zero-cost access.
module { "<std.io>" }
struct Vec2 { x: num; y: num }
impl Vec2 {
fn len(self) -> num {
return (self.x ** 2 + self.y ** 2) ** 0.5
}
fn origin() -> Vec2 { # 关联函数
return Vec2 { x: 0, y: 0 }
}
}
v = Vec2 { x: 3, y: 4 }
std.io.print(v.len()) # 5.0
o = Vec2::origin() # (0, 0)枚举是带标签的联合体,可携带数据(如 Option::Some(v))。match 被编译为跳转表或 if-else 链,必须覆盖所有变体。Enums are tagged unions that can carry data (e.g. Option::Some(v)). match compiles to a jump table or if-else chain and must cover every variant.
module { "<std.io>" }
enum Status { Ok, Warn, Err }
fn label(s: Status) -> str {
return match s {
Status::Ok => "成功"
Status::Warn => "警告"
Status::Err => "错误"
}
}
enum Shape { Circle(num); Rect(num, num) }
area = match Shape::Circle(10) {
Shape::Circle(r) => 3.14159 * r * r
Shape::Rect(w, h) => w * h
}
std.io.print(area)
std.io.print(label(Status::Err)) # "错误"switch 对整数或枚举分支,支持 case 90..=100 范围、多值 case 6, 7 与 default。分支隐式 break,不会 fall-through(除非显式 fallthrough)。switch branches on ints or enums with range (case 90..=100), multi-value (case 6, 7) and default. Implicit break — no fall-through unless fallthrough is explicit.
fn grade(score: u32) -> str {
switch (score) {
case 90..=100: "优秀"
case 80..89: "良好"
case 60..79: "及格"
default: "不及格"
}
}
fn is_weekend(day: u8) -> bool {
switch (day) {
case 6, 7: true
default: false
}
}map / filter 返回惰性迭代器,配合 list() 物化;管道操作符 |> 让数据从左到右流动,编译期展开为嵌套调用,纯语法糖。推导式直接展开为高效循环。map / filter return lazy iterators, realized with list(); the |> pipe flows data left-to-right and is pure syntax at compile time. Comprehensions lower to tight loops.
module { "<std.io>" }
nums = [1, 2, 3, 4, 5, 6]
doubled = nums
|> map(fn(x) { return x * 2 })
|> filter(fn(x) { return x > 5 })
std.io.print(list(doubled)) # [6, 8, 10, 12](map 后 filter)
squares = [x * x for x in nums if x % 2 == 0]
std.io.print(squares) # [4, 16, 36]
pairs = {k: v for k, v in zip(["a", "b"], [1, 2])}
std.io.print(pairs)惰性:map/filter 按需逐个求值,不预先分配结果数组;配合 zip、enumerate 可组合成高效数据管线。Lazy: map/filter evaluate on demand without preallocating; combine with zip, enumerate to build efficient pipelines.
堆类型赋值默认不拷贝——用 move 显式转移所有权,或用 & / &mut 借用。借用规则在编译期检查,运行时零开销。Heap types aren't copied on assignment — use move to transfer ownership explicitly, or & / &mut to borrow. Rules are checked at compile time with zero runtime cost.
module { "<std.io>" }
data = [1, 2, 3]
b = &data # 不可变借用,data 仍可用
std.io.print(b[0])
owned = move data # 转移所有权,此后 data 失效
std.io.print(owned[2])
fn read_only(x: &list[num]) { std.io.print(x.len()) }
fn modify(x: &mut list[num]) { x.append(6) }零运行时:所有权转移与借用检查完全在编译期完成,运行时没有引用计数或 GC——只要不显式使用 weak[T] 打破循环。Zero-runtime: ownership and borrow-checking happen entirely at compile time — no refcount or GC unless you opt into weak[T].
HP 的语言核心遵循「任何运行时开销都必须显式可见」。这些特性全部编译期完成:HP's core is "every runtime cost must be an explicit choice." All of these happen at compile time:
module { "<std.io>" }
const fn square(n) { return n * n }
std.io.print(square(9)) # 编译期求值
# 编译期类型断言与分支
vec = [1, 2, 3]
@compile_time_assert(@TypeOf(vec) == list[num])
macro check(n) { return n > 0 } # 宏:替代 eval 的编译期代码生成
defer cleanup() # RAII 语法糖,离开作用域自动执行
# -O3 下自动向量化、inline、兄弟/冷热路径切分、LTO、PGO 一应俱全
示例库收录了结构体、枚举、match、switch、接口、宏、defer、命名空间、FFI 与并发等真实 .hp 文件。The example corpus includes struct, enum, match, switch, interface, macro, defer, namespace, FFI and concurrency .hp files.