@@ -136,13 +136,30 @@ int fossil_jellyfish_load(fossil_jellyfish_chain *chain, const char *filepath) {
136136 return 1 ;
137137}
138138
139- // Simple Levenshtein-like distance (cost is # of mismatched chars)
140139static int fossil_jellyfish_similarity (const char * a , const char * b ) {
141- int score = 0 ;
142- for (int i = 0 ; a [i ] && b [i ]; ++ i ) {
143- if (a [i ] != b [i ]) score ++ ;
140+ int cost = 0 ;
141+ size_t i = 0 , j = 0 ;
142+
143+ while (a [i ] && b [j ]) {
144+ char ac = a [i ];
145+ char bc = b [j ];
146+
147+ // case-insensitive match
148+ if (ac >= 'A' && ac <= 'Z' ) ac += 32 ;
149+ if (bc >= 'A' && bc <= 'Z' ) bc += 32 ;
150+
151+ if (ac != bc ) {
152+ cost ++ ;
153+ }
154+ i ++ ;
155+ j ++ ;
144156 }
145- return score ;
157+
158+ // Penalty for remaining characters
159+ while (a [i ++ ]) cost ++ ;
160+ while (b [j ++ ]) cost ++ ;
161+
162+ return cost ;
146163}
147164
148165const char * fossil_jellyfish_reason_fuzzy (fossil_jellyfish_chain * chain , const char * input ) {
@@ -153,31 +170,56 @@ const char* fossil_jellyfish_reason_fuzzy(fossil_jellyfish_chain *chain, const c
153170 if (!chain -> memory [i ].valid ) continue ;
154171
155172 int score = fossil_jellyfish_similarity (input , chain -> memory [i ].input );
173+ if (score == 0 ) return chain -> memory [i ].output ; // Exact match
156174 if (score < best_score ) {
157175 best_score = score ;
158176 best_output = chain -> memory [i ].output ;
159177 }
160178 }
161179
180+ // impose a fuzzy threshold
181+ if (best_score > (int )(strlen (input ) / 2 )) {
182+ return "Unknown" ;
183+ }
184+
162185 return best_output ;
163186}
164187
165188void fossil_jellyfish_decay_confidence (fossil_jellyfish_chain * chain , float decay_rate ) {
189+ const float MIN_CONFIDENCE = 0.05f ;
190+
166191 for (size_t i = 0 ; i < chain -> count ; ++ i ) {
167192 if (!chain -> memory [i ].valid ) continue ;
168193
169- chain -> memory [i ].confidence -= decay_rate ;
170- if (chain -> memory [i ].confidence < 0.05f ) {
171- chain -> memory [i ].valid = 0 ; // mark for cleanup
194+ // Apply exponential decay
195+ chain -> memory [i ].confidence *= (1.0f - decay_rate );
196+
197+ // Clamp to zero
198+ if (chain -> memory [i ].confidence < 0.0f ) {
199+ chain -> memory [i ].confidence = 0.0f ;
200+ }
201+
202+ // Invalidate if confidence too low
203+ if (chain -> memory [i ].confidence < MIN_CONFIDENCE ) {
204+ chain -> memory [i ].valid = 0 ;
172205 }
173206 }
174207}
175208
176209const char * fossil_jellyfish_reason_chain (fossil_jellyfish_chain * chain , const char * input , int depth ) {
177- if (depth <= 0 ) return input ;
210+ const char * current = input ;
211+ const char * last_valid = input ;
178212
179- const char * first = fossil_jellyfish_reason_fuzzy (chain , input );
180- if (strcmp (first , "Unknown" ) == 0 ) return first ;
213+ for (int i = 0 ; i < depth ; ++ i ) {
214+ const char * next = fossil_jellyfish_reason_fuzzy (chain , current );
215+
216+ if (strcmp (next , "Unknown" ) == 0 || strcmp (next , current ) == 0 ) {
217+ break ;
218+ }
219+
220+ last_valid = next ;
221+ current = next ;
222+ }
181223
182- return fossil_jellyfish_reason_chain ( chain , first , depth - 1 ) ;
224+ return last_valid ;
183225}
0 commit comments