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

  // Create a VoseTree structure
  VoseTree tree;
  tree.set_max_marbles(4);

  // Create new marbles and add them to the Vose tree
  std::cerr << tree.toString();
  tree.add("red", 5L);
  std::cerr << tree.toString();
  tree.add("blue", 10L);
  std::cerr << tree.toString();
  tree.add("yellow", 20L);
  std::cerr << tree.toString();

  tree.add("red", 5L);
  std::cerr << tree.toString();
  tree.add("blue", 10L);
  std::cerr << tree.toString();
  tree.add("yellow", 20L);
  std::cerr << tree.toString();

  // Sample from the tree with and save the results to a histogram
  std::map<std::string,double> histogram;
  long hist_sum = 0L;
  for (int i = 0; i != 50000; ++i) {
    auto idx = tree.rand_marble();

    if (histogram.find(idx.label) != histogram.end()) {
      histogram[idx.label] += 1.0;
      hist_sum += 1L;
    }
    else {
      histogram.insert(std::make_pair(idx.label, 1.0));
      hist_sum += 1L;
    }
  }
  
  std::map<std::string,double> new_hist;
  std::for_each(histogram.cbegin(), histogram.cend(),
    [&new_hist,hist_sum] (std::pair<const std::string, double> a) {
      //std::cerr << a.first << ", " << (double)a.second/hist_sum << "\n";
      new_hist.insert( std::make_pair(a.first,(double)a.second/hist_sum));
  });

  std::map<std::string, double> exact_prob = tree.probabilities();
 
  // Compare the results with kl divergence
  double kl1 = VoseTree::kl(new_hist, exact_prob);
  double kl2 = VoseTree::kl(exact_prob, new_hist);
  std::cerr << "kl(histogram, exact_prob): " << kl1 << "\n";
  std::cerr << "kl(exact_prob, histogram): " << kl2 << "\n";
  
  return true;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x1f8, %rsp            # imm = 0x1F8
xorpd %xmm0, %xmm0
leaq -0x160(%rbp), %rsi
movapd %xmm0, 0x50(%rsi)
movapd %xmm0, 0x40(%rsi)
movapd %xmm0, 0x30(%rsi)
movapd %xmm0, 0x20(%rsi)
movapd %xmm0, 0x10(%rsi)
movapd %xmm0, (%rsi)
movq $0x0, 0x68(%rsi)
movq $0x4, 0x60(%rsi)
leaq -0x58(%rbp), %rdi
callq 0x374e
movq -0x58(%rbp), %rsi
movq -0x50(%rbp), %rdx
movq 0x757e(%rip), %rdi      # 0xfff0
callq 0x2200
leaq -0x48(%rbp), %r14
movq -0x10(%r14), %rdi
cmpq %r14, %rdi
je 0x8a89
callq 0x21c0
leaq -0x210(%rbp), %r15
movq %r15, -0x10(%r15)
leaq 0x288e(%rip), %rsi      # 0xb329
leaq 0x288a(%rip), %rdx      # 0xb32c
leaq -0x220(%rbp), %rdi
callq 0xa7de
leaq -0x160(%rbp), %rdi
leaq -0x220(%rbp), %rsi
movl $0x5, %edx
callq 0x259c
movq -0x220(%rbp), %rdi
cmpq %r15, %rdi
je 0x8ad7
callq 0x21c0
leaq -0x58(%rbp), %rdi
leaq -0x160(%rbp), %rsi
callq 0x374e
movq -0x58(%rbp), %rsi
movq -0x50(%rbp), %rdx
movq 0x74fa(%rip), %rdi      # 0xfff0
callq 0x2200
movq -0x58(%rbp), %rdi
cmpq %r14, %rdi
je 0x8b09
callq 0x21c0
leaq -0x1f0(%rbp), %r15
movq %r15, -0x10(%r15)
leaq 0x29e5(%rip), %rsi      # 0xb500
leaq 0x29e2(%rip), %rdx      # 0xb504
leaq -0x200(%rbp), %rdi
callq 0xa7de
leaq -0x160(%rbp), %rdi
leaq -0x200(%rbp), %rsi
movl $0xa, %edx
callq 0x259c
movq -0x200(%rbp), %rdi
cmpq %r15, %rdi
je 0x8b57
callq 0x21c0
leaq -0x58(%rbp), %rdi
leaq -0x160(%rbp), %rsi
callq 0x374e
movq -0x58(%rbp), %rsi
movq -0x50(%rbp), %rdx
movq 0x747a(%rip), %rdi      # 0xfff0
callq 0x2200
movq -0x58(%rbp), %rdi
cmpq %r14, %rdi
je 0x8b89
callq 0x21c0
leaq -0x1d0(%rbp), %r15
movq %r15, -0x10(%r15)
leaq 0x27e6(%rip), %rsi      # 0xb381
leaq 0x27e5(%rip), %rdx      # 0xb387
leaq -0x1e0(%rbp), %rdi
callq 0xa7de
leaq -0x160(%rbp), %rdi
leaq -0x1e0(%rbp), %rsi
movl $0x14, %edx
callq 0x259c
movq -0x1e0(%rbp), %rdi
cmpq %r15, %rdi
je 0x8bd7
callq 0x21c0
leaq -0x58(%rbp), %rdi
leaq -0x160(%rbp), %rsi
callq 0x374e
movq -0x58(%rbp), %rsi
movq -0x50(%rbp), %rdx
movq 0x73fa(%rip), %rdi      # 0xfff0
callq 0x2200
movq -0x58(%rbp), %rdi
cmpq %r14, %rdi
je 0x8c09
callq 0x21c0
leaq -0x1b0(%rbp), %r15
movq %r15, -0x10(%r15)
leaq 0x270e(%rip), %rsi      # 0xb329
leaq 0x270a(%rip), %rdx      # 0xb32c
leaq -0x1c0(%rbp), %rdi
callq 0xa7de
leaq -0x160(%rbp), %rdi
leaq -0x1c0(%rbp), %rsi
movl $0x5, %edx
callq 0x259c
movq -0x1c0(%rbp), %rdi
cmpq %r15, %rdi
je 0x8c57
callq 0x21c0
leaq -0x58(%rbp), %rdi
leaq -0x160(%rbp), %rsi
callq 0x374e
movq -0x58(%rbp), %rsi
movq -0x50(%rbp), %rdx
movq 0x737a(%rip), %rdi      # 0xfff0
callq 0x2200
movq -0x58(%rbp), %rdi
cmpq %r14, %rdi
je 0x8c89
callq 0x21c0
leaq -0x190(%rbp), %r15
movq %r15, -0x10(%r15)
leaq 0x2865(%rip), %rsi      # 0xb500
leaq 0x2862(%rip), %rdx      # 0xb504
leaq -0x1a0(%rbp), %rdi
callq 0xa7de
leaq -0x160(%rbp), %rdi
leaq -0x1a0(%rbp), %rsi
movl $0xa, %edx
callq 0x259c
movq -0x1a0(%rbp), %rdi
cmpq %r15, %rdi
je 0x8cd7
callq 0x21c0
leaq -0x58(%rbp), %rdi
leaq -0x160(%rbp), %rsi
callq 0x374e
movq -0x58(%rbp), %rsi
movq -0x50(%rbp), %rdx
movq 0x72fa(%rip), %rdi      # 0xfff0
callq 0x2200
movq -0x58(%rbp), %rdi
cmpq %r14, %rdi
je 0x8d09
callq 0x21c0
leaq -0x170(%rbp), %r15
movq %r15, -0x10(%r15)
leaq 0x2666(%rip), %rsi      # 0xb381
leaq 0x2665(%rip), %rdx      # 0xb387
leaq -0x180(%rbp), %rdi
callq 0xa7de
leaq -0x160(%rbp), %rdi
leaq -0x180(%rbp), %rsi
movl $0x14, %edx
callq 0x259c
movq -0x180(%rbp), %rdi
cmpq %r15, %rdi
je 0x8d57
callq 0x21c0
leaq -0x58(%rbp), %rdi
leaq -0x160(%rbp), %rsi
callq 0x374e
movq -0x58(%rbp), %rsi
movq -0x50(%rbp), %rdx
movq 0x727a(%rip), %rdi      # 0xfff0
callq 0x2200
movq -0x58(%rbp), %rdi
cmpq %r14, %rdi
je 0x8d89
callq 0x21c0
leaq -0x50(%rbp), %rcx
movl $0x0, (%rcx)
xorl %eax, %eax
movq %rax, 0x8(%rcx)
movq %rcx, 0x10(%rcx)
movq %rcx, 0x18(%rcx)
movq %rax, 0x20(%rcx)
leaq -0xb8(%rbp), %rbx
movl $0xc350, %r14d          # imm = 0xC350
leaq -0x160(%rbp), %r13
leaq -0x58(%rbp), %r12
leaq -0xc0(%rbp), %rdi
movq %r13, %rsi
callq 0x3620
movq %r12, %rdi
movq %rbx, %rsi
callq 0x69ee
leaq -0x50(%rbp), %rcx
cmpq %rcx, %rax
je 0x8dfd
movq %r12, %rdi
movq %rbx, %rsi
callq 0x46b4
movsd (%rax), %xmm0
addsd 0x2249(%rip), %xmm0     # 0xb040
movsd %xmm0, (%rax)
jmp 0x8e56
leaq -0x80(%rbp), %rax
movq %rax, -0x90(%rbp)
movq -0xb8(%rbp), %rsi
movq -0xb0(%rbp), %rdx
addq %rsi, %rdx
leaq -0x90(%rbp), %r15
movq %r15, %rdi
callq 0x4742
movabsq $0x3ff0000000000000, %rax # imm = 0x3FF0000000000000
movq %rax, -0x70(%rbp)
movq %r12, %rdi
movq %r15, %rsi
callq 0x669e
movq -0x90(%rbp), %rdi
leaq -0x80(%rbp), %rax
cmpq %rax, %rdi
je 0x8e56
callq 0x21c0
movq -0xb8(%rbp), %rdi
leaq -0xa8(%rbp), %rax
cmpq %rax, %rdi
je 0x8e6e
callq 0x21c0
decq %r14
jne 0x8dbd
movl $0x0, -0xb8(%rbp)
xorl %eax, %eax
movq %rax, -0xb0(%rbp)
movq %rbx, -0xa8(%rbp)
movq %rbx, -0xa0(%rbp)
movq %rax, -0x98(%rbp)
movq -0x40(%rbp), %rbx
leaq -0x50(%rbp), %rax
cmpq %rax, %rbx
je 0x8f77
leaq -0xe0(%rbp), %r14
leaq -0xf0(%rbp), %r13
leaq -0x90(%rbp), %r15
leaq -0xc0(%rbp), %r12
movq %r14, -0xf0(%rbp)
movq 0x20(%rbx), %rsi
movq 0x28(%rbx), %rdx
addq %rsi, %rdx
movq %r13, %rdi
callq 0x4742
movsd 0x40(%rbx), %xmm0
movsd %xmm0, -0x60(%rbp)
movsd %xmm0, -0xd0(%rbp)
leaq -0x80(%rbp), %rax
movq %rax, -0x90(%rbp)
movq -0xf0(%rbp), %rsi
movq -0xe8(%rbp), %rdx
addq %rsi, %rdx
movq %r15, %rdi
callq 0x4742
movsd -0x60(%rbp), %xmm0
divsd 0x238f(%rip), %xmm0     # 0xb2b8
movsd %xmm0, -0x70(%rbp)
movq %r12, %rdi
movq %r15, %rsi
callq 0x669e
movq -0x90(%rbp), %rdi
leaq -0x80(%rbp), %rax
cmpq %rax, %rdi
je 0x8f4e
callq 0x21c0
movq -0xf0(%rbp), %rdi
cmpq %r14, %rdi
je 0x8f5f
callq 0x21c0
movq %rbx, %rdi
callq 0x2210
movq %rax, %rbx
leaq -0x50(%rbp), %rax
cmpq %rax, %rbx
jne 0x8ecc
leaq -0x90(%rbp), %rdi
leaq -0x160(%rbp), %rsi
callq 0x3d54
leaq -0xc0(%rbp), %rdi
leaq -0x90(%rbp), %rsi
callq 0x3edc
movsd %xmm0, -0x60(%rbp)
leaq -0x90(%rbp), %rdi
leaq -0xc0(%rbp), %rsi
callq 0x3edc
movsd %xmm0, -0xc8(%rbp)
movq 0x702c(%rip), %rdi      # 0xfff0
leaq 0x24b7(%rip), %rsi      # 0xb482
movl $0x1b, %edx
callq 0x2200
movq 0x7014(%rip), %rdi      # 0xfff0
movsd -0x60(%rbp), %xmm0
callq 0x2260
leaq 0x257f(%rip), %rsi      # 0xb56c
movl $0x1, %edx
movq %rax, %rdi
callq 0x2200
movq 0x6fef(%rip), %rdi      # 0xfff0
leaq 0x2496(%rip), %rsi      # 0xb49e
movl $0x1b, %edx
callq 0x2200
movq 0x6fd7(%rip), %rdi      # 0xfff0
movsd -0xc8(%rbp), %xmm0
callq 0x2260
leaq 0x253f(%rip), %rsi      # 0xb56c
movl $0x1, %edx
movq %rax, %rdi
callq 0x2200
leaq -0x90(%rbp), %rdi
callq 0x52c6
leaq -0xc0(%rbp), %rdi
callq 0x52c6
leaq -0x58(%rbp), %rdi
callq 0x52c6
leaq -0x128(%rbp), %rbx
movq %rbx, %rdi
callq 0xa5b6
movq -0x18(%rbx), %rdi
testq %rdi, %rdi
je 0x9078
callq 0x21c0
movq -0x150(%rbp), %rax
testq %rax, %rax
je 0x9095
leaq -0x160(%rbp), %rdi
movq %rdi, %rsi
movl $0x3, %edx
callq *%rax
movb $0x1, %al
addq $0x1f8, %rsp            # imm = 0x1F8
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
movq %rax, %rdi
callq 0x4733
jmp 0x916d
jmp 0x919a
jmp 0x911e
jmp 0x9165
movq %rax, %rbx
movq -0x180(%rbp), %rdi
jmp 0x913b
jmp 0x9165
jmp 0x911e
jmp 0x9165
movq %rax, %rbx
movq -0x1a0(%rbp), %rdi
jmp 0x913b
jmp 0x9165
jmp 0x911e
jmp 0x9165
movq %rax, %rbx
movq -0x1c0(%rbp), %rdi
jmp 0x913b
jmp 0x9165
jmp 0x911e
jmp 0x9165
movq %rax, %rbx
movq -0x1e0(%rbp), %rdi
jmp 0x913b
jmp 0x9165
jmp 0x911e
jmp 0x9165
movq %rax, %rbx
movq -0x200(%rbp), %rdi
jmp 0x913b
jmp 0x9165
movq %rax, %rbx
movq -0x58(%rbp), %rdi
cmpq %r14, %rdi
jne 0x9144
jmp 0x9206
jmp 0x9165
movq %rax, %rbx
movq -0x220(%rbp), %rdi
cmpq %r15, %rdi
je 0x9206
callq 0x21c0
jmp 0x9206
jmp 0x9165
movq %rax, %rbx
leaq -0x48(%rbp), %rax
movq -0x10(%rax), %rdi
cmpq %rax, %rdi
jne 0x9144
jmp 0x9206
movq %rax, %rbx
jmp 0x9206
movq %rax, %rbx
leaq -0x90(%rbp), %rdi
callq 0x52c6
jmp 0x91cd
movq %rax, %rbx
movq -0x90(%rbp), %rdi
leaq -0x80(%rbp), %rax
cmpq %rax, %rdi
je 0x91e5
callq 0x21c0
jmp 0x91e5
jmp 0x91e2
movq %rax, %rbx
jmp 0x91cd
movq %rax, %rbx
jmp 0x91bc
movq %rax, %rbx
movq -0x90(%rbp), %rdi
leaq -0x80(%rbp), %rax
cmpq %rax, %rdi
je 0x91bc
callq 0x21c0
movq -0xf0(%rbp), %rdi
cmpq %r14, %rdi
je 0x91cd
callq 0x21c0
leaq -0xc0(%rbp), %rdi
callq 0x52c6
jmp 0x91fd
jmp 0x91e2
movq %rax, %rbx
jmp 0x91fd
movq %rax, %rbx
movq -0xb8(%rbp), %rdi
leaq -0xa8(%rbp), %rax
cmpq %rax, %rdi
je 0x91fd
callq 0x21c0
leaq -0x58(%rbp), %rdi
callq 0x52c6
leaq -0x160(%rbp), %rdi
callq 0xa43c
movq %rbx, %rdi
callq 0x22b0