Sergey, In our discussion we agreed that I check why in several EXPLAINs the value of the "rows" column changed from 1 to 0. The cause is casting. If range optimization is blocked for those queries, then the value of POSITION::records_read is 0.69999999999999996. This value is cast to ha_rows in the following place: get_best_combination() { .... /* Save records_read in JOIN_TAB so that select_describe()/etc don't have to access join->best_positions[]. */ j->records_read= (ha_rows)join->best_positions[tablenr].records_read; .... } The logic of select_describe for the "filtered" column is to set it to 0 if examined_rows is 0 (and it is because of the above). We get the number 0.6999... in best_access_path(), in the following line: /* quick_range couldn't use key! */ records= (double) s->records/rec; where: s->records = 7 rec = 10 Honestly, I don't know whether the above result is fine or not. If we should never get an estimate of 0 for the number of records, then we should use the proper rounding function (ceil for instance) instead of relying on casting. Alternatively, we should not use casting, but we should change the type of all the relevant variables/class members to double. In addition we should add to get_best_combination() a DEBUG_ASSERT(join->best_positions[tablenr].records_read > 0) to verify that we got a reasonable value. Let me know what you think, and whether I can push my fix. Timour