Split mixed array ranks into separate variable declarations (#100) - #177
Conversation
Java allows C-style array brackets on individual declarators, so a single
declaration can mix array ranks:
int multi[][] = new int[2][2], single[] = new int[2];
C# has no equivalent. Conversion failed outright with the JavaParser
assertion "The variables do not have a common type.", thrown by
getCommonType() before the visitor's own array-level check could run.
Group the declarators by array level and emit one C# declaration per
distinct rank. The groups are emitted as flat sibling statements via
PendingStatements rather than a nested block, so the declared variables
remain in the enclosing scope and stay visible to later statements.
Declarators that share a rank stay together in one declaration, and
declaration order is preserved.
This covers local variable declarations, matching the issue's repro.
Field declarations have the same limitation but the body-declaration
visitor returns a single member, so splitting them needs a wider
refactor; that remains unsupported, as noted in ArrayField.java.
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Add MixedArrayRankMultidimensional.java with the exact `int multi[][], single[]` declaration from issue #100. It is registered in GeneralSuccessfulConversionTest rather than FullIntegrationTests because jagged arrays are still emitted as rectangular C# arrays (`int[,]`) while indexing stays `multi[0][0]`, so the generated code converts but does not compile. That is the pre-existing limitation already tracked by MultidimensionalArrays.java, independent of the mixed-rank split. The runnable coverage in MixedArrayRankDeclarations.java is unchanged. Also tighten the multi-dimensional unit test to assert the two ranks land in separate declarations, instead of only checking that conversion no longer throws. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
|
Added One caveat on where it's registered: it goes in int[, ] multi = new int[2, 2]; // rectangular
int[] single = new int[2];
multi[0][0] = 1; // ...but indexed as jaggedThe mixed-rank split is correct — the two ranks land in separate declarations. What's still broken is the pre-existing jagged-vs-rectangular bug already tracked by So the coverage is now in two parts:
Also tightened the multi-dimensional unit test to assert the split explicitly ( 390 tests pass. Confirmed the new conversion test fails against the pre-fix visitor and passes with the fix. |
Fixes #100.
Problem
Java allows C-style array brackets on individual declarators, so one declaration can mix array ranks:
This failed conversion outright with
AssertionError: The variables do not have a common type.The error comes from JavaParser'sgetCommonType(), which asserts every declarator shares a type. Because it was called before the visitor's own array-level check, the friendlierInvalidOperationExceptionon the next lines was unreachable.Fix
Group declarators by array level and emit one C# declaration per distinct rank.
The groups are emitted as flat sibling statements through the existing
PendingStatementsmechanism rather than a nested block — a block would put the variables in an inner scope and break every later reference to them. Declarators that share a rank stay together in a single declaration, and declaration order is preserved.Scope
This covers local variable declarations, matching the issue's repro.
FieldDeclarationVisitorhas the same limitation, butVisitForClassreturns a singleMemberDeclarationSyntax, so splitting fields would require changing that signature across every body-declaration visitor. That felt out of scope here; fields remain unsupported, as already noted inArrayField.java.Note the pre-existing, separate limitation that jagged arrays (
int[][]) are emitted as rectangular (int[,]) while indexing stays[0][0]— that's the known issue behindMultidimensionalArrays.javabeing conversion-only, and is untouched by this PR.Testing
Unit tests — new
ConvertMixedArrayRankDeclarationTestscovers the split, same-rank grouping, declaration order and absence of a nested scope, uninitialized declarators, the #100 repro, and a regression guard that single-rank declarations are unchanged.Integration test — new
MixedArrayRankDeclarations.javaregistered inFullIntegrationTests, which compiles the generated C# with Roslyn, runs it, and asserts on stdout. It converts with no warnings.Full suite: 389 passed, 0 failed. I also confirmed 6 of the 7 new tests fail without the fix and pass with it (the 7th is the unchanged-behavior guard, which correctly passes both ways).
🤖 Generated with Claude Code