#[cfg(test)]
mod tests {
#[test]
fn test_printf_simple_with_newline() {
let c_code = r#"
printf("Hello, World!\n");
"#;
let rust_expected = r#"
println!("Hello, World!");
"#;
assert!(c_code.contains("printf(\"Hello, World!\\n\")"));
assert!(rust_expected.contains("println!(\"Hello, World!\")"));
}
#[test]
fn test_printf_without_newline() {
let c_code = r#"
printf("Hello");
"#;
let rust_expected = r#"
print!("Hello");
"#;
assert!(c_code.contains("printf(\"Hello\")"));
assert!(rust_expected.contains("print!(\"Hello\")"));
}
#[test]
fn test_printf_integer() {
let c_code = r#"
int x = 42;
printf("Value: %d\n", x);
"#;
let rust_expected = r#"
let x = 42;
println!("Value: {}", x);
"#;
assert!(c_code.contains("%d"));
assert!(rust_expected.contains("{}"));
}
#[test]
fn test_printf_string() {
let c_code = r#"
char* name = "Alice";
printf("Hello, %s!\n", name);
"#;
let rust_expected = r#"
let name = "Alice";
println!("Hello, {}!", name);
"#;
assert!(c_code.contains("%s"));
assert!(rust_expected.contains("{}"));
}
#[test]
fn test_printf_float() {
let c_code = r#"
double pi = 3.14159;
printf("Pi: %f\n", pi);
"#;
let rust_expected = r#"
let pi = 3.14159;
println!("Pi: {}", pi);
"#;
assert!(c_code.contains("%f"));
assert!(rust_expected.contains("{}"));
}
#[test]
fn test_printf_char() {
let c_code = r#"
char ch = 'A';
printf("Char: %c\n", ch);
"#;
let rust_expected = r#"
let ch = 'A';
println!("Char: {}", ch);
"#;
assert!(c_code.contains("%c"));
assert!(rust_expected.contains("{}"));
}
#[test]
fn test_printf_multiple_args() {
let c_code = r#"
printf("Name: %s, Age: %d, Score: %f\n", name, age, score);
"#;
let rust_expected = r#"
println!("Name: {}, Age: {}, Score: {}", name, age, score);
"#;
assert!(c_code.contains("%s, Age: %d, Score: %f"));
assert!(rust_expected.contains("{}, Age: {}, Score: {}"));
}
#[test]
fn test_printf_width() {
let c_code = r#"
printf("%5d\n", x);
"#;
let rust_expected = r#"
println!("{:5}", x);
"#;
assert!(c_code.contains("%5d"));
assert!(rust_expected.contains("{:5}"));
}
#[test]
fn test_printf_precision() {
let c_code = r#"
printf("%.2f\n", pi);
"#;
let rust_expected = r#"
println!("{:.2}", pi);
"#;
assert!(c_code.contains("%.2f"));
assert!(rust_expected.contains("{:.2}"));
}
#[test]
fn test_printf_zero_padding() {
let c_code = r#"
printf("%05d\n", x);
"#;
let rust_expected = r#"
println!("{:05}", x);
"#;
assert!(c_code.contains("%05d"));
assert!(rust_expected.contains("{:05}"));
}
#[test]
fn test_printf_hex() {
let c_code = r#"
printf("Hex: %x\n", value);
"#;
let rust_expected = r#"
println!("Hex: {:x}", value);
"#;
assert!(c_code.contains("%x"));
assert!(rust_expected.contains("{:x}"));
}
#[test]
fn test_printf_hex_uppercase() {
let c_code = r#"
printf("Hex: %X\n", value);
"#;
let rust_expected = r#"
println!("Hex: {:X}", value);
"#;
assert!(c_code.contains("%X"));
assert!(rust_expected.contains("{:X}"));
}
#[test]
fn test_printf_pointer() {
let c_code = r#"
printf("Pointer: %p\n", ptr);
"#;
let rust_expected = r#"
println!("Pointer: {:p}", ptr);
"#;
assert!(c_code.contains("%p"));
assert!(rust_expected.contains("{:p}"));
}
#[test]
fn test_printf_in_conditional() {
let c_code = r#"
if (x > 0) {
printf("Positive: %d\n", x);
}
"#;
let rust_expected = r#"
if x > 0 {
println!("Positive: {}", x);
}
"#;
assert!(c_code.contains("printf(\"Positive: %d\\n\", x)"));
assert!(rust_expected.contains("println!(\"Positive: {}\", x)"));
}
#[test]
fn test_printf_in_loop() {
let c_code = r#"
for (int i = 0; i < n; i++) {
printf("Index: %d\n", i);
}
"#;
let rust_expected = r#"
for i in 0..n {
println!("Index: {}", i);
}
"#;
assert!(c_code.contains("printf(\"Index: %d\\n\", i)"));
assert!(rust_expected.contains("println!(\"Index: {}\", i)"));
}
#[test]
fn test_printf_literal_only() {
let c_code = r#"
printf("Starting program...\n");
"#;
let rust_expected = r#"
println!("Starting program...");
"#;
assert!(c_code.contains("printf(\"Starting program...\\n\")"));
assert!(rust_expected.contains("println!(\"Starting program...\")"));
}
#[test]
fn test_printf_transformation_summary() {
let c_code = r#"
// Rule 1: printf with \n → println!
printf("Hello\n");
// Rule 2: printf without \n → print!
printf("Hello");
// Rule 3: %d → {}
printf("%d", x);
// Rule 4: %s → {}
printf("%s", str);
// Rule 5: %f → {}
printf("%f", pi);
// Rule 6: %c → {}
printf("%c", ch);
// Rule 7: Multiple args
printf("%s: %d\n", name, value);
// Rule 8: Width specifier
printf("%5d", x);
// Rule 9: Precision
printf("%.2f", pi);
// Rule 10: Hex format
printf("%x", value);
"#;
let rust_expected = r#"
// Rule 1: Automatic newline
println!("Hello");
// Rule 2: No newline
print!("Hello");
// Rule 3: Integer
println!("{}", x);
// Rule 4: String
println!("{}", str);
// Rule 5: Float
println!("{}", pi);
// Rule 6: Character
println!("{}", ch);
// Rule 7: Type-safe
println!("{}: {}", name, value);
// Rule 8: Width preserved
println!("{:5}", x);
// Rule 9: Precision preserved
println!("{:.2}", pi);
// Rule 10: Hex preserved
println!("{:x}", value);
"#;
assert!(c_code.contains("printf(\"Hello\\n\")"));
assert!(rust_expected.contains("println!(\"Hello\")"));
assert!(c_code.contains("%d"));
assert!(rust_expected.contains("{}"));
assert!(c_code.contains("%s"));
assert!(c_code.contains("%f"));
assert!(c_code.contains("%c"));
assert!(c_code.contains("%x"));
}
}