Fixed Group By collation

This commit is contained in:
pedrocarlo
2025-04-20 02:11:33 -03:00
parent bba9689674
commit 0df6c87f07
6 changed files with 21 additions and 4 deletions

View File

@@ -462,6 +462,7 @@ pub fn group_by_process_single_group(
start_reg_a: registers.reg_group_exprs_cmp,
start_reg_b: groups_start_reg,
count: group_by.exprs.len(),
collation: program.curr_collation(),
});
program.add_comment(

View File

@@ -1205,6 +1205,7 @@ mod tests {
notnull: false,
default: None,
unique: false,
collation: None,
}
}
fn _create_column_of_type(name: &str, ty: Type) -> Column {

View File

@@ -365,6 +365,7 @@ pub fn op_compare(
start_reg_a,
start_reg_b,
count,
collation,
} = insn
else {
unreachable!("unexpected Insn {:?}", insn)
@@ -372,6 +373,7 @@ pub fn op_compare(
let start_reg_a = *start_reg_a;
let start_reg_b = *start_reg_b;
let count = *count;
let collation = collation.unwrap_or_default();
if start_reg_a + count > start_reg_b {
return Err(LimboError::InternalError(
@@ -383,7 +385,12 @@ pub fn op_compare(
for i in 0..count {
let a = state.registers[start_reg_a + i].get_owned_value();
let b = state.registers[start_reg_b + i].get_owned_value();
cmp = Some(a.cmp(b));
cmp = match (a, b) {
(Value::Text(left), Value::Text(right)) => {
Some(collation.compare_strings(left.as_str(), right.as_str()))
}
_ => Some(a.cmp(b)),
};
if cmp != Some(std::cmp::Ordering::Equal) {
break;
}

View File

@@ -141,12 +141,13 @@ pub fn insn_to_str(
start_reg_a,
start_reg_b,
count,
collation,
} => (
"Compare",
*start_reg_a as i32,
*start_reg_b as i32,
*count as i32,
Value::build_text(""),
Value::build_text(&format!("k({count}, {})", collation.unwrap_or_default())),
0,
format!(
"r[{}..{}]==r[{}..{}]",

View File

@@ -153,6 +153,7 @@ pub enum Insn {
start_reg_a: usize,
start_reg_b: usize,
count: usize,
collation: Option<CollationSeq>,
},
/// Place the result of rhs bitwise AND lhs in third register.
BitAnd {

View File

@@ -67,19 +67,25 @@ class CollateTest(BaseModel):
"SELECT x FROM t1 WHERE a = d ORDER BY x;",
"\n".join(map(lambda x: str(x), [1, 4])),
)
limbo.run_test(
"Text comparison 'abc'=c is performed using the RTRIM collating sequence.",
"SELECT x FROM t1 WHERE 'abc' = c ORDER BY x;",
"\n".join(map(lambda x: str(x), [1, 2, 3])),
)
limbo.run_test(
"Text comparison c='abc' is performed using the RTRIM collating sequence.",
"SELECT x FROM t1 WHERE c = 'abc' ORDER BY x;",
"\n".join(map(lambda x: str(x), [1, 2, 3])),
)
limbo.run_test(
" Grouping is performed using the NOCASE collating sequence (Values 'abc', 'ABC', and 'Abc' are placed in the same group).",
"SELECT count(*) FROM t1 GROUP BY d ORDER BY 1;",
"\n".join(map(lambda x: str(x), [4])),
)
def cleanup(db_fullpath: str):
wal_path = f"{db_fullpath}-wal"