# Some useful helpers for dealing with text (arrays of characters) def equal a:text, b:text -> result:bool [ local-scope load-ingredients an:num, bn:num <- copy a, b address-equal?:boolean <- equal an, bn return-if address-equal?, 1/true return-unless a, 0/false return-unless b, 0/false a-len:num <- length *a b-len:num <- length *b # compare lengths { trace 99, [text-equal], [comparing lengths] length-equal?:bool <- equal a-len, b-len break-if length-equal? return 0 } # compare each corresponding character trace 99, [text-equal], [comparing characters] i:num <- copy 0 { done?:bool <- greater-or-equal i, a-len break-if done? a2:char <- index *a, i b2:char <- index *b, i { chars-match?:bool <- equal a2, b2 break-if chars-match? return 0 } i <- add i, 1 loop } return 1 ] scenario text-equal-reflexive [ local-scope x:text <- new [abc] run [ 10:bool/raw <- equal x, x ] memory-should-contain [ 10 <- 1 # x == x for all x ] ] scenario text-equal-identical [ local-scope x:text <- new [abc] y:text <- new [abc] run [ 10:bool/raw <- equal x, y ] memory-should-contain [ 10 <- 1 # abc == abc ] ] scenario text-equal-distinct-lengths [ local-scope x:text <- new [abc] y:text <- new [abcd] run [ 10:bool/raw <- equal x, y ] memory-should-contain [ 10 <- 0 # abc != abcd ] trace-should-contain [ text-equal: comparing lengths ] trace-should-not-contain [ text-equal: comparing characters ] ] scenario text-equal-with-empty [ local-scope x:text <- new [] y:text <- new [abcd] run [ 10:bool/raw <- equal x, y ] memory-should-contain [ 10 <- 0 # "" != abcd ] ] scenario text-equal-with-null [ local-scope x:text <- new [abcd] y:text <- copy 0 run [ 10:bool/raw <- equal x, 0 11:bool/raw <- equal 0, x 12:bool/raw <- equal x, y 13:bool/raw <- equal y, x 14:bool/raw <- equal y, y ] memory-should-contain [ 10 <- 0 11 <- 0 12 <- 0 13 <- 0 14 <- 1 ] check-trace-count-for-label 0, [error] ] scenario text-equal-common-lengths-but-distinct [ local-scope x:text <- new [abc] y:text <- new [abd] run [ 10:bool/raw <- equal x, y ] memory-should-contain [ 10 <- 0 # abc != abd ] ] # A new type to help incrementally construct texts. # todo: make this shape-shifting. container buffer [ length:num data:text ] def new-buffer capacity:num -> result:&:buffer [ local-scope load-ingredients result <- new buffer:type *result <- put *result, length:offset, 0 { break-if capacity # capacity not provided capacity <- copy 10 } data:text <- new character:type, capacity *result <- put *result, data:offset, data return result ] def grow-buffer buf:&:buffer -> buf:&:buffer [ local-scope load-ingredients # double buffer size olddata:text <- get *buf, data:offset oldlen:num <- length *olddata newlen:num <- multiply oldlen, 2 newdata:text <- new character:type, newlen *buf <- put *buf, data:offset, newdata # copy old contents i:num <- copy 0 { done?:bool <- greater-or-equal i, oldlen break-if done? src:char <- index *olddata, i *newdata <- put-index *newdata, i, src i <- add i, 1 loop } ] def buffer-full? in:&:buffer -> result:bool [ local-scope load-ingredients len:num <- get *in, length:offset s:text <- get *in, data:offset capacity:num <- length *s result <- greater-or-equal len, capacity ] # most broadly applicable definition of append to a buffer: just call to-text def append buf:&:buffer, x:_elem -> buf:&:buffer [ local-scope load-ingredients text:text <- to-text x len:num <- length *text i:num <- copy 0 { done?:bool <- greater-or-equal i, len break-if done? c:char <- index *text, i buf <- append buf, c i <- add i, 1 loop } ] def append buf:&:buffer, c:char -> buf:&:buffer [ local-scope load-ingredients len:num <- get *buf, length:offset { # backspace? just drop last character if it exists and return backspace?:bool <- equal c, 8/backspace break-unless backspace? empty?:bool <- lesser-or-equal len, 0 return-if empty? len <- subtract len, 1 *buf <- put *buf, length:offset, len return } { # grow buffer if necessary full?:bool <- buffer-full? buf break-unless full? buf <- grow-buffer buf } s:text <- get *buf, data:offset *s <- put-index *s, len, c len <- add len, 1 *buf <- put *buf, length:offset, len ] def append buf:&:buffer, t:text -> buf:&:buffer [ local-scope load-ingredients len:num <- length *t i:num <- copy 0 { done?:bool <- greater-or-equal i, len break-if done? c:char <- index *t, i buf <- append buf, c i <- add i, 1 loop } ] scenario append-to-empty-buffer [ local-scope x:&:buffer <- new-buffer run [
---
layout: layout
---
<h1>Anastasie's website!</h1>
<p>
Hi, my name is Anastasie. I'm a software engineer focused on offline-first technologies
and sustainable, uncomplicated architecture.
</p>
<p>
Some of the things I'm working on/have worked on:
<ul>
<li><a href="https://rust-lang.org">The Rust Programming Language</a> (community + organizing/moderation)</li>
<li><a href="https://github.com/rust-lang/rustlings">Rustlings</a> (maintainership)</li>
<li><a href="https://jekyllrb.com">Jekyll</a> (maintainership)</li>
<li><a href="https://nodejs.org">Node.js</a> (leadership)</li>
<li><a href="https://impfzentren.bayern">Bavarian Vaccination Centres</a> (development)</li>
<li><a href="https://jsconf.eu">JSConf EU</a> and <a href="https://cssconf.eu">CSSconf EU</a> (organizing)</li>
<li><a href="https://berline.rs">Rust Berlin</a> (organizing)</li>
</ul>
</p>
<p>
You can contact me via email: <code>ana at this website</code>
</p>