This is a fib calculation code copied from https://github.com/drujensen/fib repo.
fn fib(n i64) i64 {
if n <= 1 {
return 1
}
return fib(n - 1) + fib(n - 2)
}
fn main() {
println(fib(46))
}
Results:
➜ v --version
V 0.1.24 0d93eeb
➜ time v fib.v
v fib.v 0.21s user 0.02s system 99% cpu 0.221 total
➜ time ./fib
2971215073
./fib 9.22s user 0.00s system 99% cpu 9.219 total
The nim, rust, c etc runs around 4s in my pc.
v takes around 9s.
It builds fast, but falls behind on release/optimization flags.
For example, A look at rust with some optimization flags. It build faster and ran faster.
➜ time rustc -C opt-level=s fib.rs
rustc -C opt-level=s fib.rs 0.12s user 0.02s system 97% cpu 0.140 total
➜ time ./fib
2971215073
./fib 4.99s user 0.00s system 99% cpu 4.997 total
Now let's see the c,
➜ gcc -o fib fib.c
➜ time ./fib
2971215073
./fib 9.26s user 0.00s system 99% cpu 9.258 total
The v and c had almost same results. However C supports optimization flags.
➜ gcc -Ofast -o fib fib.c
➜ time ./fib
2971215073
./fib 4.11s user 0.00s system 99% cpu 4.112 total
Which means v is falling behind without the flags.
If there are indeed some flags, it should be documented.
Though it's mentioned in the homepage,
"In the future V will have its own optimizer."
Is there an ETA for this?
v -prod fib.v
6.25s on my PC. but seems that my PC is little bit slower than yours.
Many thanks for showing.
I don't know if I missed anything. It did increase the speed, but not close to the c/rust build. Since it was mentioned "As fast as C".
➜ v --prod fib.v
➜ time ./fib
2971215073
./fib 9.13s user 0.00s system 99% cpu 9.135 total
➜ v -prod fib.v
➜ time ./fib
2971215073
./fib 5.08s user 0.00s system 99% cpu 5.081 total
Moreover, if you didn't mention, I wouldn't even known about this flag since it was hidden away :D . Then I searched for it and saw it was mentioned few times in whole codebase, and only once in the https://github.com/vlang/v/blob/2006995020181425a8b3476dd01b16059a7ab419/doc/docs.md#L157 file.
I think we still need different optimization flags and document them.
btw 4s and 5s doesn't seem much, bit it will be a lot when we put a even bigger number, or start doing heavier calculations, for example going through a 1GB json data with lots of loops.
Here is a benchmark using hyperfine for future discussion,
➜ cd v
➜ alias v=~/Downloads/v_linux/v
➜ v -prod fib.v
➜ hyperfine "./fib"
Benchmark #1: ./fib
Time (mean ± σ): 5.105 s ± 0.023 s [User: 5.103 s, System: 0.002 s]
Range (min … max): 5.087 s … 5.158 s 10 runs
➜ cd c
➜ gcc -Ofast -o fib fib.c
➜ hyperfine "./fib"
Benchmark #1: ./fib
Time (mean ± σ): 4.148 s ± 0.026 s [User: 4.146 s, System: 0.001 s]
Range (min … max): 4.107 s … 4.194 s 10 runs
The compiler is not even finished... we need a lot of improvements.
Yes i think there is a lot of initialization work. I think if we could decrease the initialization we could save some time.
It's documented under v help build, will copy it to v help as well.
The speed should be the same as with C, I'm also getting a 1s difference. Will investigate, pretty sure that's something easy to fix.
A hello world in V is 8339 lines of code in V.
Only because all the builtin modules are re-compiled for each program. This will be fixed with module caching by tomorrow.
Shouldn't impact performance.
Could it be, that the _vinit method takes some time?
No, just profiled it.
@entrptaher if u64 is used, like in C, then the performance is the same.
Would be great if you could submit a PR there.
It's still missing by around 100~250ms though. But I tested it with u64 and results have improved.
Benchmark #1: ./fib
Time (mean ± σ): 4.345 s ± 0.018 s [User: 4.342 s, System: 0.001 s]
Range (min … max): 4.310 s … 4.364 s 10 runs
i made a PR there
Hmm, v has a 200ms overhead for this program for some reason. I guess it's understandable though.
➜ v -cflags "-Ofast" fib.v
➜ time ./fib
2971215073
./fib 4.35s user 0.00s system 99% cpu 4.355 total
It should be literally the same, it compiles to the same code.
You are using time and benchmark. Use benchmark for both programs.
The only overhead V has is some consts initialization, which should be less than 1 ms.
In that case, I am not sure what I'm doing wrong here to get such difference. The reason 46 is choosen is because that is the minimum fib number that produces such huge result 2971215073.
I just changed it to u64, and tried using both -prod and -cflags as you can see.
fn fib(n u64) u64 {
if n <= 1 {
return 1
}
return fib(n - 1) + fib(n - 2)
}
fn main() {
println(fib(46))
}
➜ v --version
V 0.1.24 0d93eeb
➜ v -cflags "-Ofast" fib.v
➜ hyperfine "./fib"
Benchmark #1: ./fib
Time (mean ± σ): 4.377 s ± 0.008 s [User: 4.376 s, System: 0.000 s]
Range (min … max): 4.367 s … 4.390 s 10 runs
➜ v -prod fib.v
➜ hyperfine "./fib"
Benchmark #1: ./fib
Time (mean ± σ): 4.323 s ± 0.012 s [User: 4.322 s, System: 0.001 s]
Range (min … max): 4.313 s … 4.353 s 10 runs
#include <stdio.h>
#include <stdint.h>
static uint64_t fib(uint64_t n) {
if (n <= 1) return 1;
return fib(n - 1) + fib(n - 2);
}
int main(void) {
printf("%lu \n", fib(46));
return 0;
}
➜ gcc --version
gcc (Ubuntu 9.2.1-9ubuntu2) 9.2.1 20191008
➜ gcc -Ofast -o fib fib.c
➜ hyperfine "./fib"
Benchmark #1: ./fib
Time (mean ± σ): 4.147 s ± 0.024 s [User: 4.146 s, System: 0.001 s]
Range (min … max): 4.105 s … 4.178 s 10 runs
v -prod -show_c_cmd fib.v
Here is a result from the command, I ran it twice.
➜ v -prod -show_c_cmd fib.v
==========
cc -std=gnu11 -Wall -Wextra -Wno-unused-variable -Wno-unused-parameter -Wno-unused-result -Wno-unused-function -Wno-missing-braces -Wno-unused-label -O3 -fno-strict-aliasing -flto -Werror=implicit-function-declaration -o "fib" "/home/taher/.cache/v/fib.tmp.c" -lm -lpthread -ldl
cc took 583 ms
=========
➜ v -prod -show_c_cmd fib.v
==========
cc -std=gnu11 -Wall -Wextra -Wno-unused-variable -Wno-unused-parameter -Wno-unused-result -Wno-unused-function -Wno-missing-braces -Wno-unused-label -O3 -fno-strict-aliasing -flto -Werror=implicit-function-declaration -o "fib" "/home/taher/.cache/v/fib.tmp.c" -lm -lpthread -ldl
cc took 251 ms
=========
I changed my computer to a different one to test if this was only happening on my pc or not. It is indeed missing 200ms.
➜ hyperfine --warmup 3 ./fib
Benchmark #1: ./fib
Time (mean ± σ): 4.791 s ± 0.050 s [User: 4.791 s, System: 0.000 s]
Range (min … max): 4.765 s … 4.901 s 10 runs
➜ hyperfine --warmup 3 ./fib
Benchmark #1: ./fib
Time (mean ± σ): 4.577 s ± 0.004 s [User: 4.576 s, System: 0.001 s]
Range (min … max): 4.574 s … 4.588 s 10 runs
Most helpful comment
No, just profiled it.
@entrptaher if
u64is used, like in C, then the performance is the same.Would be great if you could submit a PR there.