Comparison of V and Other Languages

I created V because none of the existing languages had all of the following features:

Fast compilation D, Go, Delphi Simplicity & maintainability Go Great performance on par with C and

zero cost C interop C, C++, D, Delphi, Rust Safety (immutability, no null, option types, free from data races) Rust Easy concurrency Go Easy cross compilation Go Compile time code generation D Small compiler with zero dependencies - No global state - Hot code reloading -

Initially I was going to compare V to all major languages, but it got repetitive pretty quickly.

The table above and the list of the features on the home page should give you a pretty good picture.

For example, it's pretty obvious that compared to C++, V is much much simpler. It offers up to 400 times faster compilation, safety, lack of undefined behavior, easy concurrency, compile time code generation, etc.

Compared to Python, it's much faster, simpler, safer, more maintainable, etc.

You can use this formula for any language.

Syntax comparison:

V for Go developers

V for C++ developers

Since V is very similar to Go, and its domain is similar to Rust's, I left a comparison with these two languages.





Go

V is very similar to Go, and these are the things it improves upon:

- No global state



- No null

- No undefined values

- No err != nil checks (replaced by option types)

- Immutability by default

- Only one declaration style ( a := 0 )

- Much smaller runtime

- Much smaller binaries (a simple web server written in V is 65 KB vs 7 MB in Go)

- Zero cost C interop

- No GC

- Much faster serialization using codegen and no runtime reflection

- Precompiled HTML templates unlike html/template s that have to be parsed on every request

- Fearless concurrency (no data race guarantee at compilation) wip

- Enums

- Generics

- String interpolation: println('$foo: $bar.baz')

- Stricter vfmt to ensure one coding style

- Centralised package manager





Rust

Rust has a very different philosophy.

It is a complex language with a growing set of features and a steep learning curve. No doubt, once you learn and understand the language, it becomes a very powerful tool for developing safe, fast, and stable software. But the complexity is still there.

V's goal is to allow building maintainable and predictable software. That's why the language is so simple and maybe even boring for some. The good thing is, you can jump into any part of the project and understand what's going on, feel like it was you who wrote it, because the language is simple and there's only one way of doing things.

Rust's compilation speed is slow, on par with C++. V compiles 1.2 million lines of code per cpu per second.

V vs Rust vs Go: Example

Since V's domain is close to both Go and Rust, I decided to use a simple example to compare the three.

It's a simple program that fetches top Hacker News stories concurrently.

Rust

use serde::Deserialize; use std::sync::{Arc, Mutex}; const STORIES_URL: &str = "https://hacker-news.firebaseio.com/v0/topstories.json"; const ITEM_URL_BASE: &str = "https://hacker-news.firebaseio.com/v0/item"; #[derive(Deserialize)] struct Story { title: String, } fn main() { let story_ids: Arc<Vec<u64>> = Arc::new(reqwest::get(STORIES_URL).unwrap().json().unwrap()); let cursor = Arc::new(Mutex::new(0)); let mut handles = Vec::new(); for _ in 0..8 { let cursor = cursor.clone(); let story_ids = story_ids.clone(); handles.push(std::thread::spawn(move || loop { let index = { let mut cursor_guard = cursor.lock().unwrap(); let index = *cursor_guard; if index >= story_ids.len() { return; } *cursor_guard += 1; index }; let story_url = format!("{}/{}.json", ITEM_URL_BASE, story_ids[index]); let story: Story = reqwest::get(&story_url).unwrap().json().unwrap(); println!("{}", story.title); })); } for handle in handles { handle.join().unwrap(); } }

package main import ( "encoding/json" "fmt" "io/ioutil" "net/http" "sync" ) const STORIES_URL = "https://hacker-news.firebaseio.com/v0/topstories.json" const ITEM_URL_BASE = "https://hacker-news.firebaseio.com/v0/item" type Story struct { Title string } func main() { rsp, err := http.Get(STORIES_URL) if err != nil { panic(err) } defer rsp.Body.Close() data, err := ioutil.ReadAll(rsp.Body) if err != nil { panic(err) } var ids []int if err := json.Unmarshal(data, &ids); err != nil { panic(err) } var cursor int var mutex sync.Mutex next := func() int { mutex.Lock() defer mutex.Unlock() temp := cursor cursor++ return temp } wg := sync.WaitGroup{} for i := 0; i < 8; i++ { wg.Add(1) go func() { for cursor := next(); cursor < len(ids); cursor = next() { url := fmt.Sprintf( "%s/%d.json", ITEM_URL_BASE, ids[cursor], ) rsp, err := http.Get(url) if err != nil { panic(err) } defer rsp.Body.Close() data, err := ioutil.ReadAll(rsp.Body) if err != nil { panic(err) } var story Story if err := json.Unmarshal(data, &story); err != nil { panic(err) } fmt.Println(story.Title) } wg.Done() }() } wg.Wait() }

const ( StoriesUrl = 'https://hacker-news.firebaseio.com/v0/topstories.json' ItemUrlBase = 'https://hacker-news.firebaseio.com/v0/item' ) struct Story { title string } fn main() { resp := http.get(StoriesUrl)? ids := json.decode([]int, resp.body)? mut cursor := 0 for _ in 0..8 { go fn() { for { lock { if cursor >= ids.len { break } id := ids[cursor] cursor++ } resp := http.get('$ItemUrlBase/$id.json')? story := json.decode(Story, resp.body)? println(story.title) } }() } runtime.wait() }