// File: cegme[P]vose/test.cc
// Function: test::test6()
bool test::test6() {

  VoseTree tree;
  tree.set_max_marbles(4);
  tree.set_max_bags(5);

  // Generate a set of label names.
  std::string labels = "red yellow blue";

  // Make a random number generator for marble weights
  std::default_random_engine weight_generator(VoseUtil::RANDOM_SEED); 
  std::uniform_int_distribution<long>
    weight_distribution(1, 1000);
  std::function<long()> random_weight =
    std::bind(weight_distribution, weight_generator);

  // FIXME why does 280 node work? Where is the error, need more stats
  for(size_t i = 0; i != 279; ++i) {
    // Get a random marble with random label and random weight.
    size_t weight = random_weight();
    //std::cerr << "label_idx: " << label_idx << ", " << labels[label_idx] << "\n";
    //std::cerr << " weight: " << weight << "\n";
    std::random_shuffle(labels.begin(), labels.end());
    tree.add(labels, weight);
    //std::cerr << tree.toString();
  }

  // Generate a histogram.
  auto hist = VoseTree::histogram(tree, 50000L);

  // Get the real probabilities
  auto prob = tree.probabilities();

  // Compare the results
  double kl1 = VoseTree::kl(hist, prob);
  double kl2 = VoseTree::kl(prob, hist);
  std::cerr << "kl(hist, prob): " << kl1 << "\n";
  std::cerr << "kl(prob, hist): " << kl2 << "\n";
  return true;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x270, %rsp            # imm = 0x270
movq %rdi, -0x8(%rbp)
leaq -0x78(%rbp), %rdi
movq %rdi, -0x228(%rbp)
callq 0x18660
movq -0x228(%rbp), %rdi
movl $0x4, %esi
callq 0x186f0
jmp 0x17982
leaq -0x78(%rbp), %rdi
movl $0x5, %esi
callq 0x18750
jmp 0x17992
leaq -0xa9(%rbp), %rdi
movq %rdi, -0x230(%rbp)
callq 0x2300
movq -0x230(%rbp), %rdx
leaq 0x4af2(%rip), %rsi      # 0x1c4a5
leaq -0xa8(%rbp), %rdi
callq 0x2270
jmp 0x179c1
leaq -0xa9(%rbp), %rdi
callq 0x2240
movq 0x137ec(%rip), %rsi     # 0x2b1c0
leaq -0xb8(%rbp), %rdi
callq 0x4a30
jmp 0x179e2
leaq -0xc8(%rbp), %rdi
movl $0x1, %esi
movl $0x3e8, %edx            # imm = 0x3E8
callq 0x18880
jmp 0x179fa
leaq -0x100(%rbp), %rdi
leaq -0xc8(%rbp), %rsi
leaq -0xb8(%rbp), %rdx
callq 0x188b0
jmp 0x17a16
leaq -0xe8(%rbp), %rdi
leaq -0x100(%rbp), %rsi
callq 0x188f0
jmp 0x17a2b
movq $0x0, -0x108(%rbp)
cmpq $0x117, -0x108(%rbp) # imm = 0x117
je 0x17b79
leaq -0xe8(%rbp), %rdi
callq 0x189d0
movq %rax, -0x238(%rbp)
jmp 0x17a5c
movq -0x238(%rbp), %rax
movq %rax, -0x110(%rbp)
leaq -0xa8(%rbp), %rdi
movq %rdi, -0x240(%rbp)
callq 0x21c0
movq -0x240(%rbp), %rdi
movq %rax, -0x118(%rbp)
callq 0x2120
movq %rax, -0x120(%rbp)
movq -0x118(%rbp), %rdi
movq -0x120(%rbp), %rsi
callq 0x18b10
jmp 0x17aac
leaq -0x140(%rbp), %rdi
leaq -0xa8(%rbp), %rsi
callq 0x20e0
jmp 0x17ac1
movq -0x110(%rbp), %rdx
leaq -0x78(%rbp), %rdi
leaq -0x140(%rbp), %rsi
callq 0x24f0
jmp 0x17ada
leaq -0x140(%rbp), %rdi
callq 0x2140
movq -0x108(%rbp), %rax
addq $0x1, %rax
movq %rax, -0x108(%rbp)
jmp 0x17a36
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x80(%rbp)
movl %eax, -0x84(%rbp)
jmp 0x17d6c
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x80(%rbp)
movl %eax, -0x84(%rbp)
leaq -0xa9(%rbp), %rdi
callq 0x2240
jmp 0x17d6c
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x80(%rbp)
movl %eax, -0x84(%rbp)
jmp 0x17d60
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x80(%rbp)
movl %eax, -0x84(%rbp)
jmp 0x17d54
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x80(%rbp)
movl %eax, -0x84(%rbp)
leaq -0x140(%rbp), %rdi
callq 0x2140
jmp 0x17d54
leaq -0x1e0(%rbp), %rdi
leaq -0x78(%rbp), %rsi
callq 0x18a10
jmp 0x17b8b
leaq -0x170(%rbp), %rdi
leaq -0x1e0(%rbp), %rsi
movl $0xc350, %edx           # imm = 0xC350
callq 0x3880
jmp 0x17ba5
leaq -0x1e0(%rbp), %rdi
callq 0x18710
leaq -0x210(%rbp), %rdi
leaq -0x78(%rbp), %rsi
callq 0x3460
jmp 0x17bc3
leaq -0x170(%rbp), %rdi
leaq -0x210(%rbp), %rsi
callq 0x3630
movsd %xmm0, -0x248(%rbp)
jmp 0x17be0
movsd -0x248(%rbp), %xmm0
movsd %xmm0, -0x218(%rbp)
leaq -0x210(%rbp), %rdi
leaq -0x170(%rbp), %rsi
callq 0x3630
movsd %xmm0, -0x250(%rbp)
jmp 0x17c0d
movsd -0x250(%rbp), %xmm0
movsd %xmm0, -0x220(%rbp)
movq 0x133cc(%rip), %rdi     # 0x2aff0
leaq 0x4858(%rip), %rsi      # 0x1c483
callq 0x2210
movq %rax, -0x258(%rbp)
jmp 0x17c39
movq -0x258(%rbp), %rdi
movsd -0x218(%rbp), %xmm0
callq 0x2320
movq %rax, -0x260(%rbp)
jmp 0x17c56
movq -0x260(%rbp), %rdi
leaq 0x48b8(%rip), %rsi      # 0x1c51c
callq 0x2210
jmp 0x17c6b
movq 0x1337e(%rip), %rdi     # 0x2aff0
leaq 0x481b(%rip), %rsi      # 0x1c494
callq 0x2210
movq %rax, -0x268(%rbp)
jmp 0x17c87
movq -0x268(%rbp), %rdi
movsd -0x220(%rbp), %xmm0
callq 0x2320
movq %rax, -0x270(%rbp)
jmp 0x17ca4
movq -0x270(%rbp), %rdi
leaq 0x486a(%rip), %rsi      # 0x1c51c
callq 0x2210
jmp 0x17cb9
leaq -0x210(%rbp), %rdi
callq 0x5050
leaq -0x170(%rbp), %rdi
callq 0x5050
leaq -0xe8(%rbp), %rdi
callq 0x18ad0
leaq -0xa8(%rbp), %rdi
callq 0x2140
leaq -0x78(%rbp), %rdi
callq 0x18710
movb $0x1, %al
andb $0x1, %al
addq $0x270, %rsp            # imm = 0x270
popq %rbp
retq
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x80(%rbp)
movl %eax, -0x84(%rbp)
leaq -0x1e0(%rbp), %rdi
callq 0x18710
jmp 0x17d54
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x80(%rbp)
movl %eax, -0x84(%rbp)
jmp 0x17d48
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x80(%rbp)
movl %eax, -0x84(%rbp)
leaq -0x210(%rbp), %rdi
callq 0x5050
leaq -0x170(%rbp), %rdi
callq 0x5050
leaq -0xe8(%rbp), %rdi
callq 0x18ad0
leaq -0xa8(%rbp), %rdi
callq 0x2140
leaq -0x78(%rbp), %rdi
callq 0x18710
movq -0x80(%rbp), %rdi
callq 0x22f0
nop