// File: /workspace/github_cpp_makefile_star2_O3/samuel500[P]NEAT/species.cpp
// Function: Species::evolve(std::vector<Node*, std::allocator<Node*>>*, std::vector<Connection*, std::allocator<Connection*>>*)
vector<Individual*> Species::evolve(vector<Node*> *all_nodes, vector<Connection*> *all_connections){

	vector<Individual*> new_individuals;

	vector<Node*>::iterator nodePtr;
	vector<Connection*>::iterator conPtr;


	// percentage of species members whose descendants go on to the next generation
	// probably should be set somewhere else
	double p_mating = 0.5; 

	sort(members.begin(), members.end(), indPtr_compare);


	Individual *new_individual;

	// cout << "ev1" << endl;

	while(new_individuals.size() < n_offspring){

		int n_parent = randint((int)(p_mating*members.size()), members.size()-1);


		new_individual = new Individual(*members[n_parent]);


		// cout << "ev2" << endl;

		new_individual->mutate(all_nodes, all_connections);
		// cout << "ev3" << endl;

		for(conPtr=new_individual->connections.begin(); conPtr!=new_individual->connections.end(); ++conPtr){
			all_connections->push_back((*conPtr));
		}

		for(nodePtr=new_individual->nodes.begin(); nodePtr!=new_individual->nodes.end(); ++nodePtr){
			all_nodes->push_back((*nodePtr));
		}
		// cout << "ev4" << endl;

		new_individuals.push_back(new_individual);


		if(n_offspring > 5 && new_individuals.size()<n_offspring){
			new_individual = new Individual(*members[members.size()-1]);
			new_individuals.push_back(new_individual);

			for(conPtr=new_individual->connections.begin(); conPtr!=new_individual->connections.end(); ++conPtr){
				all_connections->push_back((*conPtr));
			}
			for(nodePtr=new_individual->nodes.begin(); nodePtr!=new_individual->nodes.end(); ++nodePtr){
				all_nodes->push_back((*nodePtr));
			}
			// cout << "ev5" << endl;

		}
	}


	// rep = members[members.size()-1];

	vector<Individual*>::iterator indPtr;

	// for(indPtr=members.begin(); indPtr!=prev(members.end()); ++indPtr){
	// 	delete *indPtr;
	// }

	// members.clear();

	return new_individuals;


}

// Assembly:
pushq %rbp
movq %rsp, %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x28, %rsp
movq %rcx, %r14
movq %rdx, %r15
movq %rdi, %rbx
xorpd %xmm0, %xmm0
movupd %xmm0, (%rdi)
movq $0x0, 0x10(%rdi)
movq (%rsi), %r13
movq %rsi, -0x40(%rbp)
movq 0x8(%rsi), %r12
cmpq %r12, %r13
je 0x4746
movq %r12, %rax
subq %r13, %rax
sarq $0x3, %rax
bsrq %rax, %rdx
xorl $0x3f, %edx
addl %edx, %edx
xorq $0x7e, %rdx
leaq -0x8f8(%rip), %rcx      # 0x3e24
movq %r13, %rdi
movq %r12, %rsi
callq 0x3173
leaq -0x90a(%rip), %rdx      # 0x3e24
movq %r13, %rdi
movq %r12, %rsi
callq 0x329e
movq 0x8(%rbx), %rax
subq (%rbx), %rax
sarq $0x3, %rax
jmp 0x4748
xorl %eax, %eax
movq -0x40(%rbp), %rdx
movslq 0x40(%rdx), %rcx
cmpq %rcx, %rax
jae 0x497f
movq %rbx, -0x30(%rbp)
movq (%rdx), %r12
movq 0x8(%rdx), %rbx
callq 0x1040
movl %eax, -0x44(%rbp)
movl $0x98, %edi
callq 0x1100
movq %rax, %r13
subq %r12, %rbx
sarq $0x3, %rbx
movq %rbx, %xmm0
punpckldq 0x28f3(%rip), %xmm0 # xmm0 = xmm0[0],mem[0],xmm0[1],mem[1]
subpd 0x28fb(%rip), %xmm0     # 0x7090
movapd %xmm0, %xmm1
unpckhpd %xmm0, %xmm1            # xmm1 = xmm1[1],xmm0[1]
addsd %xmm0, %xmm1
mulsd 0x2a3f(%rip), %xmm1     # 0x71e8
cvttsd2si %xmm1, %ecx
subl %ecx, %ebx
movl -0x44(%rbp), %eax
cltd
idivl %ebx
addl %ecx, %edx
movslq %edx, %rax
movq -0x40(%rbp), %rcx
movq (%rcx), %rcx
movq (%rcx,%rax,8), %rsi
movq %r13, %rdi
callq 0x5718
movq %r13, -0x38(%rbp)
movq %r13, %rdi
movq %r15, %rsi
movq %r14, %rdx
callq 0x5c64
movq -0x38(%rbp), %rax
movq 0x60(%rax), %r13
cmpq 0x68(%rax), %r13
je 0x481a
movq 0x8(%r14), %rsi
cmpq 0x10(%r14), %rsi
je 0x4805
movq (%r13), %rax
movq %rax, (%rsi)
addq $0x8, 0x8(%r14)
jmp 0x4810
movq %r14, %rdi
movq %r13, %rdx
callq 0x2bbe
addq $0x8, %r13
movq -0x38(%rbp), %rax
jmp 0x47e7
movq 0x18(%rax), %r13
cmpq 0x20(%rax), %r13
movq -0x30(%rbp), %rbx
je 0x4859
movq 0x8(%r15), %rsi
cmpq 0x10(%r15), %rsi
je 0x4840
movq (%r13), %rax
movq %rax, (%rsi)
addq $0x8, 0x8(%r15)
jmp 0x484b
movq %r15, %rdi
movq %r13, %rdx
callq 0x2cfe
addq $0x8, %r13
movq -0x38(%rbp), %rax
cmpq 0x20(%rax), %r13
jne 0x4828
movq 0x8(%rbx), %rsi
cmpq 0x10(%rbx), %rsi
je 0x486d
movq %rax, (%rsi)
addq $0x8, 0x8(%rbx)
jmp 0x4879
movq %rbx, %rdi
leaq -0x38(%rbp), %rdx
callq 0x2eda
movq -0x40(%rbp), %rax
movslq 0x40(%rax), %rax
cmpq $0x6, %rax
movq -0x30(%rbp), %rbx
jl 0x4963
movq 0x8(%rbx), %rcx
subq (%rbx), %rcx
sarq $0x3, %rcx
cmpq %rax, %rcx
jae 0x4963
movl $0x98, %edi
callq 0x1100
movq %rax, %r12
movq -0x40(%rbp), %rax
movq 0x8(%rax), %rax
movq -0x8(%rax), %rsi
movq %r12, %rdi
callq 0x5718
movq %r12, -0x38(%rbp)
movq -0x30(%rbp), %rdi
movq 0x8(%rdi), %rsi
cmpq 0x10(%rdi), %rsi
je 0x48e0
movq %r12, (%rsi)
addq $0x8, 0x8(%rdi)
jmp 0x48e9
leaq -0x38(%rbp), %rdx
callq 0x2eda
movq -0x38(%rbp), %rax
movq 0x60(%rax), %r13
cmpq 0x68(%rax), %r13
je 0x4924
movq 0x8(%r14), %rsi
cmpq 0x10(%r14), %rsi
je 0x490f
movq (%r13), %rax
movq %rax, (%rsi)
addq $0x8, 0x8(%r14)
jmp 0x491a
movq %r14, %rdi
movq %r13, %rdx
callq 0x2bbe
addq $0x8, %r13
movq -0x38(%rbp), %rax
jmp 0x48f1
movq 0x18(%rax), %r13
cmpq 0x20(%rax), %r13
movq -0x30(%rbp), %rbx
je 0x4963
movq 0x8(%r15), %rsi
cmpq 0x10(%r15), %rsi
je 0x494a
movq (%r13), %rax
movq %rax, (%rsi)
addq $0x8, 0x8(%r15)
jmp 0x4955
movq %r15, %rdi
movq %r13, %rdx
callq 0x2cfe
addq $0x8, %r13
movq -0x38(%rbp), %rax
cmpq 0x20(%rax), %r13
jne 0x4932
movq 0x8(%rbx), %rax
subq (%rbx), %rax
sarq $0x3, %rax
movq -0x40(%rbp), %rdx
movslq 0x40(%rdx), %rcx
cmpq %rcx, %rax
jb 0x475d
movq %rbx, %rax
addq $0x28, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
jmp 0x49b8
movq %rax, %r14
movl $0x98, %esi
movq %r12, %rdi
jmp 0x49ab
movq %rax, %r14
movl $0x98, %esi
movq %r13, %rdi
callq 0x1110
jmp 0x49c0
jmp 0x49b8
jmp 0x49bd
jmp 0x49bd
movq %rax, %r14
jmp 0x49c4
movq %rax, %r14
movq -0x30(%rbp), %rbx
movq (%rbx), %rdi
testq %rdi, %rdi
je 0x49d8
movq 0x10(%rbx), %rsi
subq %rdi, %rsi
callq 0x1110
movq %r14, %rdi
callq 0x11a0