// File: /workspace/github_c_makefile_star2_O2/chatziko-k08[P]lecture-code/tests/ADTSet_test.c
// Function: test_find
void test_find(void) {
	
	Set set = set_create(compare_ints, free);

	int N = 1000;

	int** value_array = malloc(N * sizeof(*value_array));

	for (int i = 0; i < N; i++)
		value_array[i] = create_int(i);

	// Παρόμοια με την set_remove, εάν το δέντρο δεν είναι σωστά ισορροπημένο, οι συναρτήσεις εύρεσης
	// στοιχείων δεν θα ελέγχονται πλήρως
	shuffle(value_array, N);

	for (int i = 0; i < N; i++) {
		set_insert(set, value_array[i]);

		SetNode found_node 	= set_find_node(set, value_array[i]);
		Pointer found_value = set_node_value(set, found_node);

		TEST_ASSERT(found_node != SET_EOF);
		TEST_ASSERT(found_value == value_array[i]);
	}

	// Αναζήτηση στοιχείου που δεν υπάρχει στο set
	int not_exists = 2000;
	TEST_ASSERT(set_find_node(set, &not_exists) == SET_EOF);
	TEST_ASSERT(set_find(set, &not_exists) == NULL);

	// Αναζήτηση μέγιστων/ελάχιστων στοιχείων
	// Συγκρίνουμε τις τιμές των δεικτών και όχι τους ίδιους τους δείκτες, καθώς
	// δεν γνωρίζουμε την θέση τους μετά απο το ανακάτεμα του πίνακα, αλλά γνωρίζουμε
	// ποιές τιμές υπάρχουν στο Set. Στη συγκεκριμένη περίπτωση, γνωρίζουμε ότι Set = {0, 1, ..., N-1}
	SetNode first_node = set_first(set);
	Pointer first_value = set_node_value(set, first_node);
	TEST_ASSERT((*(int *)first_value) == 0);

	SetNode next = set_next(set, first_node);
	Pointer next_value = set_node_value(set, next);
	TEST_ASSERT((*(int *)next_value) == 1);

	SetNode last_node = set_last(set);
	Pointer last_node_value = set_node_value(set, last_node);
	TEST_ASSERT((*(int *)last_node_value) == N-1);

	SetNode prev = set_previous(set, last_node);
	Pointer prev_value = set_node_value(set, prev);
	TEST_ASSERT((*(int *)prev_value) == N-2);

	// Ελέγχουμε και ότι βρίσκουμε σωστά τις τιμές από ενδιάμεσους κόμβους
	SetNode middle_node = set_find_node(set, value_array[N/2]);
	SetNode middle_node_prev = set_previous(set, middle_node);

	Pointer middle_node_value = set_node_value(set, middle_node);
	Pointer middle_node_value_prev = set_node_value(set, middle_node_prev);
	
	TEST_ASSERT(*(int *)middle_node_value == *(int *)middle_node_value_prev + 1);


	set_destroy(set);
	free(value_array);
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x18, %rsp
leaq -0x4de(%rip), %rdi      # 0x3a80
movq 0x605b(%rip), %rsi      # 0x9fc0
callq 0x4b08
movq %rax, %rbx
movl $0x1f40, %edi           # imm = 0x1F40
callq 0x21a0
movq %rax, %r13
xorl %r14d, %r14d
cmpq $0x3e8, %r14            # imm = 0x3E8
je 0x3f98
movl %r14d, %edi
callq 0x3a71
movq %rax, (%r13,%r14,8)
incq %r14
jmp 0x3f7d
movq %rbx, 0x8(%rsp)
movq %r13, %rdi
movl $0x3e8, %esi            # imm = 0x3E8
callq 0x3b0c
leaq 0x2367(%rip), %rbp      # 0x6318
leaq 0x26d3(%rip), %r15      # 0x668b
xorl %ebx, %ebx
movq %r13, 0x10(%rsp)
cmpq $0x3e8, %rbx            # imm = 0x3E8
je 0x4060
movq (%r13,%rbx,8), %r13
movq 0x8(%rsp), %r14
movq %r14, %rdi
movq %r13, %rsi
callq 0x4dc8
movq %r14, %rdi
movq %r13, %rsi
callq 0x4b6e
movq %rbp, %r12
movq %rax, %rbp
movq %r14, %rdi
movq %rax, %rsi
callq 0x5197
movq %rax, %r14
xorl %edi, %edi
testq %rbp, %rbp
movq %r12, %rbp
setne %dil
movq %r12, %rsi
movl $0xb4, %edx
movq %r15, %rcx
leaq 0x240c(%rip), %r8       # 0x642a
xorl %eax, %eax
callq 0x239c
testl %eax, %eax
je 0x405b
xorl %edi, %edi
cmpq %r13, %r14
sete %dil
movq %rbp, %rsi
movl $0xb5, %edx
movq %r15, %rcx
leaq 0x23fc(%rip), %r8       # 0x6440
xorl %eax, %eax
callq 0x239c
incq %rbx
testl %eax, %eax
movq 0x10(%rsp), %r13
jne 0x3fbf
callq 0x2bc0
leaq 0x4(%rsp), %rsi
movl $0x7d0, (%rsi)          # imm = 0x7D0
movq 0x8(%rsp), %rbx
movq %rbx, %rdi
callq 0x4b6e
xorl %edi, %edi
testq %rax, %rax
sete %dil
leaq 0x2290(%rip), %rsi      # 0x6318
leaq 0x25fc(%rip), %rcx      # 0x668b
leaq 0x23c8(%rip), %r8       # 0x645e
movl $0xba, %edx
xorl %eax, %eax
callq 0x239c
testl %eax, %eax
je 0x405b
leaq 0x4(%rsp), %rsi
movq %rbx, %rdi
callq 0x4b5a
xorl %edi, %edi
testq %rax, %rax
sete %dil
leaq 0x2255(%rip), %rsi      # 0x6318
leaq 0x25c1(%rip), %rcx      # 0x668b
leaq 0x23b8(%rip), %r8       # 0x6489
movl $0xbb, %edx
xorl %eax, %eax
callq 0x239c
testl %eax, %eax
je 0x405b
movq %rbx, %rdi
callq 0x4ca2
movq %rax, %r15
movq %rbx, %rdi
movq %rax, %rsi
callq 0x5197
xorl %edi, %edi
cmpl $0x0, (%rax)
sete %dil
leaq 0x220d(%rip), %rsi      # 0x6318
leaq 0x2579(%rip), %rcx      # 0x668b
leaq 0x2393(%rip), %r8       # 0x64ac
movl $0xc3, %edx
xorl %eax, %eax
callq 0x239c
testl %eax, %eax
je 0x405b
movq %rbx, %rdi
movq %r15, %rsi
callq 0x50b4
movq %rbx, %rdi
movq %rax, %rsi
callq 0x5197
xorl %edi, %edi
cmpl $0x1, (%rax)
sete %dil
leaq 0x21c5(%rip), %rsi      # 0x6318
leaq 0x2531(%rip), %rcx      # 0x668b
leaq 0x2366(%rip), %r8       # 0x64c7
movl $0xc7, %edx
xorl %eax, %eax
callq 0x239c
testl %eax, %eax
je 0x405b
movq %rbx, %rdi
callq 0x4cbf
movq %rax, %r15
movq %rbx, %rdi
movq %rax, %rsi
callq 0x5197
xorl %edi, %edi
cmpl $0x3e7, (%rax)          # imm = 0x3E7
sete %dil
leaq 0x217a(%rip), %rsi      # 0x6318
leaq 0x24e6(%rip), %rcx      # 0x668b
leaq 0x2335(%rip), %r8       # 0x64e1
movl $0xcb, %edx
xorl %eax, %eax
callq 0x239c
testl %eax, %eax
je 0x405b
movq %rbx, %rdi
movq %r15, %rsi
callq 0x4fd8
movq %rbx, %rdi
movq %rax, %rsi
callq 0x5197
xorl %edi, %edi
cmpl $0x3e6, (%rax)          # imm = 0x3E6
sete %dil
leaq 0x212f(%rip), %rsi      # 0x6318
leaq 0x249b(%rip), %rcx      # 0x668b
leaq 0x230b(%rip), %r8       # 0x6502
movl $0xcf, %edx
xorl %eax, %eax
callq 0x239c
testl %eax, %eax
je 0x405b
movq 0xfa0(%r13), %rsi
movq %rbx, %rdi
callq 0x4b6e
movq %rax, %r14
movq %rbx, %rdi
movq %rax, %rsi
callq 0x4fd8
movq %rax, %r15
movq %rbx, %rdi
movq %r14, %rsi
callq 0x5197
movq %rax, %r14
movq %rbx, %rdi
movq %r15, %rsi
callq 0x5197
movl (%rax), %eax
incl %eax
xorl %edi, %edi
cmpl %eax, (%r14)
sete %dil
leaq 0x20c0(%rip), %rsi      # 0x6318
leaq 0x242c(%rip), %rcx      # 0x668b
leaq 0x22b8(%rip), %r8       # 0x651e
movl $0xd8, %edx
xorl %eax, %eax
callq 0x239c
testl %eax, %eax
je 0x405b
movq %rbx, %rdi
callq 0x4ce1
movq %r13, %rdi
callq 0x22a0
addq $0x18, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq