Browse code

Add actual sorting of results

John Hawthorn authored on 13/07/2014 01:49:21
Showing 1 changed files

  • fzy.c index 06a3717..acbda60 100644
... ...
@@ -14,9 +14,14 @@ double match(const char *needle, const char *haystack);
14 14
 int choices_capacity = 0;
15 15
 int choices_n = 0;
16 16
 const char **choices = NULL;
17
+double *choices_score = NULL;
18
+size_t *choices_sorted = NULL;
17 19
 
18 20
 void resize_choices(int new_capacity){
19 21
 	choices = realloc(choices, new_capacity * sizeof(const char *));
22
+	choices_score = realloc(choices_score, new_capacity * sizeof(double));
23
+	choices_sorted = realloc(choices_sorted, new_capacity * sizeof(size_t));
24
+
20 25
 	int i = choices_capacity;
21 26
 	for(; i < new_capacity; i++){
22 27
 		choices[i] = NULL;
... ...
@@ -48,14 +53,36 @@ void read_choices(){
48 53
 	free(line);
49 54
 }
50 55
 
56
+size_t choices_available = 0;
57
+
58
+static int cmpchoice(const void *p1, const void *p2) {
59
+	size_t idx1 = *(size_t *)p1;
60
+	size_t idx2 = *(size_t *)p2;
61
+
62
+	double score1 = choices_score[idx1];
63
+	double score2 = choices_score[idx2];
64
+
65
+	if(score1 == score2)
66
+		return 0;
67
+	else if(score1 < score2)
68
+		return 1;
69
+	else
70
+		return -1;
71
+}
72
+
73
+
51 74
 void run_search(char *needle){
75
+	choices_available = 0;
52 76
 	int i;
53 77
 	for(i = 0; i < choices_n; i++){
54
-		double rank = match(needle, choices[i]);
55
-		if(rank > 0){
56
-			printf("%s\n", choices[i]);
78
+		choices_score[i] = match(needle, choices[i]);
79
+		if(choices_score[i] >= 0.0){
80
+			choices_sorted[choices_available++] = i;
57 81
 		}
58 82
 	}
83
+
84
+	qsort(choices_sorted, choices_available, sizeof(size_t), cmpchoice);
85
+
59 86
 }
60 87
 
61 88
 int ttyin;
... ...
@@ -112,12 +139,10 @@ void draw(){
112 139
 	const char *prompt = "> ";
113 140
 	clear();
114 141
 	fprintf(ttyout, "%s%s\n", prompt, search);
115
-	for(i = 0; line < 10 && i < choices_n; i++){
116
-		double rank = match(search, choices[i]);
117
-		if(rank > 0){
118
-			fprintf(ttyout, "%s\n", choices[i]);
119
-			line++;
120
-		}
142
+	run_search(search);
143
+	for(i = 0; line < 10 && i < choices_available; i++){
144
+		fprintf(ttyout, "%s\n", choices[choices_sorted[i]]);
145
+		line++;
121 146
 	}
122 147
 	fprintf(ttyout, "%c%c%iA", 0x1b, '[', line + 1);
123 148
 	fprintf(ttyout, "%c%c%iG", 0x1b, '[', strlen(prompt) + strlen(search) + 1);
... ...
@@ -128,18 +153,15 @@ void emit(){
128 153
 	/* ttyout should be flushed before outputting on stdout */
129 154
 	fclose(ttyout);
130 155
 
131
-	int i;
132
-	for(i = 0; i < choices_n; i++){
133
-		double rank = match(search, choices[i]);
134
-		if(rank > 0){
135
-			/* Output the first match */
136
-			printf("%s\n", choices[i]);
137
-			exit(EXIT_SUCCESS);
138
-		}
156
+	run_search(search);
157
+	if(choices_available){
158
+		/* output the first result */
159
+		printf("%s\n", choices[choices_sorted[0]]);
160
+	}else{
161
+		/* No match, output the query instead */
162
+		printf("%s\n", search);
139 163
 	}
140 164
 
141
-	/* No match, output the query instead */
142
-	printf("%s\n", search);
143 165
 	exit(EXIT_SUCCESS);
144 166
 }
145 167