├── rust ├── .gitignore ├── Cargo.toml ├── Cargo.lock └── src │ └── main.rs ├── python3 └── heap.py ├── python2 └── heap.py ├── ruby └── heap.rb ├── perl └── heap.pl ├── go └── heap.go ├── cpp └── heap.cpp ├── d └── heap.d ├── swift └── heap.swift ├── javascript └── heap.js ├── LICENSE ├── scala └── heap.scala ├── php └── heap.php ├── pascal └── heap.pas ├── java └── Heap.java ├── README.md └── csharp └── Heap.cs /rust/.gitignore: -------------------------------------------------------------------------------- 1 | target 2 | -------------------------------------------------------------------------------- /rust/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "rust" 3 | version = "0.1.0" 4 | authors = ["Gulshan Singh "] 5 | 6 | [dependencies] 7 | time = "*" 8 | -------------------------------------------------------------------------------- /python3/heap.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | def pushDown(h, pos, n): 4 | while 2 * pos + 1 < n: 5 | j = 2 * pos + 1 6 | if j + 1 < n and h[j+1] > h[j]: 7 | j += 1 8 | if h[pos] >= h[j]: 9 | break 10 | h[pos], h[j] = h[j], h[pos] 11 | pos = j 12 | 13 | if __name__ == "__main__": 14 | start = time.clock() 15 | N = 10000000 16 | h = list(range(N)) 17 | for i in range(N//2, -1, -1): 18 | pushDown(h, i, N) 19 | n = N 20 | while n > 1: 21 | n -= 1 22 | h[0], h[n] = h[n], h[0] 23 | pushDown(h, 0, n) 24 | for i in range(N): 25 | assert(h[i] == i) 26 | print("Done in %f" % ((time.clock() - start) * 1000)) 27 | -------------------------------------------------------------------------------- /python2/heap.py: -------------------------------------------------------------------------------- 1 | import time 2 | 3 | def pushDown(h, pos, n): 4 | while 2 * pos + 1 < n: 5 | j = 2 * pos + 1 6 | if j + 1 < n and h[j+1] > h[j]: 7 | j += 1 8 | if h[pos] >= h[j]: 9 | break 10 | h[pos], h[j] = h[j], h[pos] 11 | pos = j 12 | 13 | if __name__ == "__main__": 14 | start = time.clock() 15 | N = 10000000 16 | h = list(range(N)) 17 | for i in xrange(N//2, -1, -1): 18 | pushDown(h, i, N) 19 | n = N 20 | while n > 1: 21 | n -= 1 22 | h[0], h[n] = h[n], h[0] 23 | pushDown(h, 0, n) 24 | for i in xrange(N): 25 | assert(h[i] == i) 26 | print("Done in %f" % ((time.clock() - start) * 1000)) 27 | -------------------------------------------------------------------------------- /rust/Cargo.lock: -------------------------------------------------------------------------------- 1 | [root] 2 | name = "rust" 3 | version = "0.1.0" 4 | dependencies = [ 5 | "time 0.1.25 (registry+https://github.com/rust-lang/crates.io-index)", 6 | ] 7 | 8 | [[package]] 9 | name = "gcc" 10 | version = "0.3.5" 11 | source = "registry+https://github.com/rust-lang/crates.io-index" 12 | 13 | [[package]] 14 | name = "libc" 15 | version = "0.1.6" 16 | source = "registry+https://github.com/rust-lang/crates.io-index" 17 | 18 | [[package]] 19 | name = "time" 20 | version = "0.1.25" 21 | source = "registry+https://github.com/rust-lang/crates.io-index" 22 | dependencies = [ 23 | "gcc 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)", 24 | "libc 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", 25 | ] 26 | 27 | -------------------------------------------------------------------------------- /ruby/heap.rb: -------------------------------------------------------------------------------- 1 | N = 10000000.freeze 2 | $h = Array.new 3 | 4 | def pushDown(pos, n) 5 | while 2*pos + 1 < n 6 | j = 2*pos + 1 7 | if (j+1 < n) and ($h[j+1] > $h[j]) 8 | j += 1 9 | end 10 | 11 | break unless $h[pos] < $h[j] 12 | 13 | $h[pos], $h[j] = $h[j], $h[pos] 14 | pos = j 15 | end 16 | end 17 | 18 | def main 19 | start = Time.now 20 | 21 | N.times do |i| 22 | $h << i 23 | end 24 | 25 | (N/2).downto(0) do |i| 26 | pushDown i, N 27 | end 28 | 29 | n = N 30 | while n > 1 31 | $h[0], $h[n-1] = $h[n-1], $h[0] 32 | n -= 1 33 | pushDown 0, n 34 | end 35 | 36 | N.times do |i| 37 | raise "h[i] != i" unless $h[i] == i 38 | end 39 | 40 | puts "Done in #{((Time.now - start) * 1000).to_i}" 41 | end 42 | 43 | begin 44 | main 45 | end 46 | -------------------------------------------------------------------------------- /perl/heap.pl: -------------------------------------------------------------------------------- 1 | #!/usr/bin/perl 2 | 3 | use warnings; 4 | use strict; 5 | use Time::HiRes qw(gettimeofday); 6 | 7 | my $start_time = gettimeofday; 8 | 9 | my $N = 10000000; 10 | my @a; 11 | 12 | sub pushDown { 13 | my ($pos, $N) = @_; 14 | while (2 * $pos + 1 < $N) { 15 | my $j = 2 * $pos + 1; 16 | if ($j + 1 < $N && $a[$j + 1] > $a[$j]) { 17 | ++$j; 18 | } 19 | last if $a[$pos] >= $a[$j]; 20 | @a[$pos, $j] = @a[$j, $pos]; 21 | $pos = $j; 22 | } 23 | } 24 | 25 | @a = 0 .. $N-1; 26 | 27 | pushDown($_, $N) for reverse 0 .. $N / 2; 28 | 29 | my $n = $N; 30 | while ($n > 1) { 31 | @a[0, $n - 1] = @a[$n - 1, 0]; 32 | --$n; 33 | pushDown(0, $n); 34 | } 35 | 36 | while (my ($id, $key) = each @a) { 37 | die unless $id == $key; 38 | } 39 | 40 | my $end_time = gettimeofday; 41 | print "Done in ", int(1000 * ($end_time - $start_time)), " ms\n"; 42 | -------------------------------------------------------------------------------- /go/heap.go: -------------------------------------------------------------------------------- 1 | package main 2 | 3 | import ( 4 | "fmt" 5 | "time" 6 | ) 7 | 8 | const N = 10000000 9 | 10 | func pushDown(h []int, pos, n int) { 11 | for 2*pos + 1 < n { 12 | j := 2 * pos + 1 13 | if j + 1 < n && h[j+1] > h[j] { 14 | j++ 15 | } 16 | if h[pos] >= h[j] { 17 | break 18 | } 19 | 20 | h[pos], h[j] = h[j], h[pos] 21 | pos = j 22 | } 23 | } 24 | 25 | func main() { 26 | start := time.Now() 27 | 28 | h := make([]int, N) 29 | for i := 0; i < N; i++ { 30 | h[i] = i 31 | } 32 | 33 | for i := N/2; i >= 0; i-- { 34 | pushDown(h, i, N) 35 | } 36 | 37 | n := N 38 | for n > 1 { 39 | n-- 40 | h[0], h[n] = h[n], h[0] 41 | pushDown(h, 0, n) 42 | } 43 | 44 | for i := 0; i < N; i++ { 45 | if h[i] != i { 46 | panic("h[i] != i") 47 | } 48 | } 49 | 50 | end := time.Since(start) 51 | fmt.Println("Done in", end.Nanoseconds() / 1000000.0) 52 | } 53 | -------------------------------------------------------------------------------- /cpp/heap.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | #define forn(i, n) for (int i = 0; i < int(n); i++) 6 | 7 | using namespace std; 8 | 9 | const int N = 10000000; 10 | 11 | int h[N]; 12 | 13 | void pushDown(int pos, int n) 14 | { 15 | while (2 * pos + 1 < n) 16 | { 17 | int j = 2 * pos + 1; 18 | if (j + 1 < n && h[j + 1] > h[j]) 19 | j++; 20 | if (h[pos] >= h[j]) 21 | break; 22 | swap(h[pos], h[j]); 23 | pos = j; 24 | } 25 | } 26 | 27 | int main() 28 | { 29 | forn(i, N) 30 | h[i] = i; 31 | 32 | for (int i = N / 2; i >= 0; i--) 33 | pushDown(i, N); 34 | 35 | int n = N; 36 | while (n > 1) 37 | { 38 | swap(h[0], h[n - 1]); 39 | n--; 40 | pushDown(0, n); 41 | } 42 | 43 | forn(i, N) 44 | assert(h[i] == i); 45 | 46 | cout << "Done in " << clock() * 1000 / CLOCKS_PER_SEC << endl; 47 | } 48 | -------------------------------------------------------------------------------- /d/heap.d: -------------------------------------------------------------------------------- 1 | import std.algorithm; 2 | import std.datetime; 3 | import std.exception; 4 | import std.stdio; 5 | 6 | immutable int N = 10_000_000; 7 | 8 | __gshared int [] h; 9 | 10 | void pushDown (int pos, int n) 11 | { 12 | while (2 * pos + 1 < n) 13 | { 14 | int j = 2 * pos + 1; 15 | if (j + 1 < n && h[j + 1] > h[j]) 16 | { 17 | j++; 18 | } 19 | if (h[pos] >= h[j]) 20 | { 21 | break; 22 | } 23 | swap (h[pos], h[j]); 24 | pos = j; 25 | } 26 | } 27 | 28 | void main () 29 | { 30 | auto sw = StopWatch (AutoStart.yes); 31 | 32 | h = new int [N]; 33 | foreach (i; 0..N) 34 | { 35 | h[i] = i; 36 | } 37 | 38 | for (int i = N / 2; i >= 0; i--) 39 | { 40 | pushDown (i, N); 41 | } 42 | 43 | int n = N; 44 | while (n > 1) 45 | { 46 | swap (h[0], h[n - 1]); 47 | n--; 48 | pushDown (0, n); 49 | } 50 | 51 | foreach (i; 0..N) 52 | { 53 | enforce (h[i] == i); 54 | } 55 | 56 | sw.stop (); 57 | 58 | writeln (sw.peek ().msecs); 59 | } 60 | -------------------------------------------------------------------------------- /swift/heap.swift: -------------------------------------------------------------------------------- 1 | import Foundation; 2 | 3 | let N: Int = 10000000 4 | var h = [Int](repeating: 0, count: N) 5 | 6 | func pushDown(_ pos_: Int, _ n: Int) -> Void { 7 | var pos: Int = pos_ 8 | while 2 * pos + 1 < n { 9 | var j: Int = 2 * pos + 1 10 | if j + 1 < n && h[j + 1] > h[j] { 11 | j += 1 12 | } 13 | if h[pos] >= h[j] { 14 | break; 15 | } 16 | h.swapAt(pos, j) 17 | pos = j; 18 | } 19 | } 20 | 21 | func main() -> Void { 22 | let start = DispatchTime.now() 23 | 24 | for i in 0.. 1 { 34 | h.swapAt(0, n - 1) 35 | n -= 1 36 | pushDown(0, n) 37 | } 38 | 39 | for i in 0.. h[j]) 9 | j++; 10 | if (h[pos] >= h[j]) 11 | break; 12 | var t = h[pos]; 13 | h[pos] = h[j]; 14 | h[j] = t; 15 | pos = j; 16 | } 17 | } 18 | 19 | function main() { 20 | var start = Date.now(); 21 | 22 | for (var i = 0; i < N; i++) { 23 | h[i] = i; 24 | } 25 | 26 | for (var i = N / 2; i >= 0; i--) 27 | pushDown(i, N); 28 | 29 | var n = N; 30 | 31 | while (n > 1) { 32 | var t = h[0]; 33 | h[0] = h[n - 1]; 34 | h[n - 1] = t; 35 | 36 | n--; 37 | pushDown(0, n); 38 | } 39 | 40 | for (var i = 0; i < N; i++) { 41 | if (h[i] != i) { 42 | throw new RuntimeException("h[i] != i"); 43 | } 44 | } 45 | 46 | print("Done in " + (Date.now() - start)); 47 | } 48 | 49 | main(); 50 | -------------------------------------------------------------------------------- /rust/src/main.rs: -------------------------------------------------------------------------------- 1 | extern crate time; 2 | use time::Duration; 3 | 4 | fn main() { 5 | let duration = Duration::span(|| { 6 | let n: i32 = 10000000; 7 | let mut h: Vec = (0..n).collect(); 8 | 9 | make_heap(&mut *h); 10 | 11 | for i in (1..n as usize).rev() { 12 | h.swap(0, i); 13 | push_down(0, i, &mut *h); 14 | } 15 | 16 | for (elt, i) in h.iter().zip(0..n) { 17 | assert!(*elt == i); 18 | } 19 | }); 20 | println!("Done in {}", duration.num_milliseconds()); 21 | } 22 | 23 | fn make_heap(h: &mut [i32]) { 24 | for i in (0..h.len() / 2).rev() { 25 | push_down(i, h.len(), h); 26 | } 27 | } 28 | 29 | fn push_down(mut pos: usize, size: usize, h: &mut [i32]) { 30 | while 2 * pos + 1 < size { 31 | let mut vic = 2 * pos + 1; 32 | if vic + 1 < size && h[vic + 1] > h[vic] { 33 | vic += 1; 34 | } 35 | 36 | if h[pos] > h[vic] { 37 | break; 38 | } 39 | 40 | h.swap(pos, vic); 41 | pos = vic; 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2013 Mike Mirzayanov 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy of 6 | this software and associated documentation files (the "Software"), to deal in 7 | the Software without restriction, including without limitation the rights to 8 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 9 | the Software, and to permit persons to whom the Software is furnished to do so, 10 | subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 17 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 18 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 19 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 20 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 21 | -------------------------------------------------------------------------------- /scala/heap.scala: -------------------------------------------------------------------------------- 1 | // Author: Wizmann 2 | 3 | import scala.annotation.tailrec 4 | 5 | object Heap { 6 | val N = 10000000 7 | val h = (0 until N).toArray 8 | 9 | def main(args: Array[String]) { 10 | val st = System.nanoTime 11 | 12 | (0 to N/2).reverse.foreach(pushDown(_, N)) 13 | (2 to N).reverse.foreach(i => { 14 | arraySwap(h, 0, i - 1); 15 | pushDown(0, i - 1) 16 | }) 17 | (0 until N).foreach(x => assert(h(x) == x)) 18 | 19 | val end = System.nanoTime 20 | println("Done in " + ((end - st)/1e6).toLong) 21 | } 22 | 23 | @tailrec 24 | def pushDown(pos: Int, n: Int) { 25 | val j = left(pos); 26 | if (j < n) { 27 | val next = if (j + 1 < n && h(j + 1) > h(j)) j + 1 else j 28 | 29 | if (h(pos) < h(next)) { 30 | arraySwap(h, pos, next) 31 | pushDown(next, n) 32 | } 33 | } 34 | } 35 | def arraySwap(ll: Array[Int], a: Int, b: Int) { 36 | val t = ll(a) 37 | ll(a) = ll(b) 38 | ll(b) = t 39 | } 40 | def left(x: Int): Int = 2 * x + 1 41 | def right(x: Int): Int = 2 * x + 2 42 | } 43 | -------------------------------------------------------------------------------- /php/heap.php: -------------------------------------------------------------------------------- 1 | $h[$j]) 13 | $j++; 14 | if ($h[$pos] >= $h[$j]) 15 | break; 16 | $t = $h[$pos]; 17 | $h[$pos] = $h[$j]; 18 | $h[$j] = $t; 19 | $pos = $j; 20 | } 21 | } 22 | 23 | function main() { 24 | global $h; 25 | 26 | $start = round(microtime(true) * 1000); 27 | 28 | for ($i = 0; $i < N; $i++) { 29 | $h[$i] = $i; 30 | } 31 | 32 | for ($i = (int) (N / 2); $i >= 0; $i--) { 33 | pushDown($i, N); 34 | } 35 | 36 | $n = N; 37 | while ($n > 1) { 38 | $n--; 39 | $t = $h[0]; 40 | $h[0] = $h[$n]; 41 | $h[$n] = $t; 42 | pushDown(0, $n); 43 | } 44 | 45 | foreach ($h as $i => $v) { 46 | if ($i !== $v) { 47 | echo "Sorting failed at index $i!\n"; 48 | return; 49 | } 50 | } 51 | 52 | $finish = round(microtime(true) * 1000); 53 | $delta = $finish - $start; 54 | 55 | echo "Done in $delta\n"; 56 | } 57 | 58 | main(); 59 | -------------------------------------------------------------------------------- /pascal/heap.pas: -------------------------------------------------------------------------------- 1 | uses 2 | SysUtils, DateUtils; 3 | 4 | const 5 | MAXN = 10000000; 6 | 7 | var 8 | h: array[0..MAXN - 1] of LongInt; 9 | 10 | procedure pushDown(pos, n: LongInt); 11 | var 12 | j, t: LongInt; 13 | begin 14 | while 2 * pos + 1 < n do 15 | begin 16 | j := 2 * pos + 1; 17 | if (j + 1 < n) and (h[j + 1] > h[j]) then 18 | inc(j); 19 | 20 | if h[pos] >= h[j] then 21 | break; 22 | 23 | t := h[pos]; 24 | h[pos] := h[j]; 25 | h[j] := t; 26 | 27 | pos := j; 28 | end; 29 | end; 30 | 31 | var 32 | i, n, t: LongInt; 33 | start: TDateTime; 34 | begin 35 | start := now; 36 | 37 | for i := 0 to MAXN - 1 do 38 | h[i] := i; 39 | 40 | for i := (MAXN div 2) downto 0 do 41 | pushDown(i, MAXN); 42 | 43 | n := MAXN; 44 | while n > 1 do 45 | begin 46 | t := h[0]; 47 | h[0] := h[n - 1]; 48 | h[n - 1] := t; 49 | 50 | dec(n); 51 | pushDown(0, n); 52 | end; 53 | 54 | for i := 0 to MAXN - 1 do 55 | if h[i] <> i then begin 56 | writeln('fail: h[', i, '] != ', i); 57 | halt(1); 58 | end; 59 | 60 | writeln('Done in ', MilliSecondsBetween(start, now)); 61 | end. 62 | -------------------------------------------------------------------------------- /java/Heap.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @author Mike Mirzayanov (mirzayanovmr@gmail.com) 3 | */ 4 | public class Heap { 5 | private static final int N = 10000000; 6 | private static final int[] h = new int[N]; 7 | 8 | private static void pushDown(int pos, int n) { 9 | while (2 * pos + 1 < n) { 10 | int j = 2 * pos + 1; 11 | if (j + 1 < n && h[j + 1] > h[j]) 12 | j++; 13 | if (h[pos] >= h[j]) 14 | break; 15 | int t = h[pos]; 16 | h[pos] = h[j]; 17 | h[j] = t; 18 | pos = j; 19 | } 20 | } 21 | 22 | public static void main(String[] args) { 23 | long start = System.currentTimeMillis(); 24 | 25 | for (int i = 0; i < N; i++) { 26 | h[i] = i; 27 | } 28 | 29 | for (int i = N / 2; i >= 0; i--) 30 | pushDown(i, N); 31 | 32 | int n = N; 33 | while (n > 1) { 34 | int t = h[0]; 35 | h[0] = h[n - 1]; 36 | h[n - 1] = t; 37 | n--; 38 | pushDown(0, n); 39 | } 40 | 41 | for (int i = 0; i < N; i++) { 42 | if (h[i] != i) { 43 | throw new RuntimeException("h[i] != i"); 44 | } 45 | } 46 | 47 | System.out.println("Done in " + (System.currentTimeMillis() - start)); 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | binary-heap-benchmark 2 | ===================== 3 | 4 | Collection of binary heap sort implementation for many languages, primary to compare performance between languages 5 | 6 | ### Results 7 | 8 | Programs have been executed on http://codeforces.com/ which uses Intel(R) Core(TM) i5-3470 CPU @ 3.20GHz on Windows 7 64-bit. 9 | 10 | You may use http://codeforces.com/problemset/customtest to run a code. 11 | 12 | Several executions give the following results: 13 | 14 | |Language|Compiler|Running time, ms| 15 | |--------|--------|------------| 16 | |C++ |MinGW 4.7.2 32-bit| 630 | 17 | |C++ |MS VS 2010 32-bit| 650 | 18 | |Java |Oracle Java 6 32-bit| 1060 | 19 | |Java |Oracle Java 7 32-bit| 1050 | 20 | |Java |Oracle Java 8 32-bit| 1000 | 21 | |JavaScript | V8 3.23.0 32-bit| 1700 | 22 | |Pascal | Delphi 7 32-bit| 630 | 23 | |Pascal | FreePascal 2.6.2 32-bit | 730 | 24 | |Python 2 | Python 2.7.4 32-bit | 125000 | 25 | |Python 3 | Python 3.3.2 32-bit | 200000 | 26 | |Ruby | Ruby 1.9.3p0 (2011-10-30, i386-mingw32) 32-bit | 520000 | 27 | |Ruby | Ruby 2.0.0p353 (2013-11-22, i386-mingw32) 32-bit | 345000 | 28 | |Scala | Scala 2.10.3 (over Oracle Java 7 32-bit) | 1550 | 29 | |Go | Go 1.2 32-bit | 1780 | 30 | |D | DMD v2.064.2 32-bit | 800 | 31 | |C# | Mono 2.10.9 32-bit | 850 | 32 | |C# | MS CSC .Net 4.5.1 64-bit | 850 | 33 | |Perl | Perl v5.12.2 for MSWin32-x86-multi-thread | 195000 | 34 | -------------------------------------------------------------------------------- /csharp/Heap.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Diagnostics; 3 | 4 | namespace HeapBenchmark 5 | { 6 | class Heap 7 | { 8 | private const int N = 10000000; 9 | private static int[] h = new int[N]; 10 | 11 | private static void PushDown(int pos, int n) 12 | { 13 | while (2*pos + 1 < n) 14 | { 15 | int j = 2*pos + 1; 16 | if (j + 1 < n && h[j + 1] > h[j]) 17 | j++; 18 | if (h[pos] >= h[j]) 19 | break; 20 | int t = h[pos]; 21 | h[pos] = h[j]; 22 | h[j] = t; 23 | pos = j; 24 | } 25 | } 26 | 27 | public static void Main(String[] args) 28 | { 29 | var sw = Stopwatch.StartNew(); 30 | 31 | for (int i = 0; i < N; i++) 32 | h[i] = i; 33 | 34 | for (int i = N/2; i >= 0; i--) 35 | PushDown(i, N); 36 | 37 | int n = N; 38 | while (n > 1) 39 | { 40 | int t = h[0]; 41 | h[0] = h[n - 1]; 42 | h[n - 1] = t; 43 | n--; 44 | PushDown(0, n); 45 | } 46 | 47 | for (int i = 0; i < N; i++) 48 | { 49 | if (h[i] != i) 50 | throw new Exception("h[i] != i"); 51 | } 52 | 53 | Console.WriteLine("Done in " + sw.ElapsedMilliseconds); 54 | } 55 | } 56 | } 57 | --------------------------------------------------------------------------------