Problem overview
The method PrintRhombus takes an odd positive integer n and prints n lines, each exactly n characters wide, forming a diamond of stars. For n = 5 the lines are two spaces, one star, two spaces; then one space, three stars, one space; then five stars; and the pattern shrinks back down. The statement points out that the spaces at the end of each line matter, so every line must be padded to the full width.
In the listing below, square brackets are added only so the trailing spaces can be seen. The method itself prints no brackets.
[ * ]
[ *** ]
[*****]
[ *** ]
[ * ]
Approach: track stars and spaces per line
Every line has the same shape: some spaces, some stars, and the same number of spaces again. Because the shape is symmetrical, two numbers describe each line: stars and spaces (the number of spaces on each side). Their relation is stars + 2 * spaces = n.
The first line has one star and n / 2 spaces on each side. Moving down through the top half, each line has one more star on each side, so stars grows by 2, and spaces shrinks by 1. From the middle line on, it runs in reverse. Repeating a character a given number of times is needed three times per line, so it goes into a helper, BuildString.
Tracing n = 5, with the values used to print each line:
Line i | spaces | stars |
|---|---|---|
| 0 | 2 | 1 |
| 1 | 1 | 3 |
| 2 | 0 | 5 |
| 3 | 1 | 3 |
| 4 | 2 | 1 |
Step by step
- Start with one star.
int stars = 1;is the count for the first line. - Compute the side spaces.
int spaces = n / 2;. Dividing twointvalues drops the remainder, so5 / 2is2. Sincenis odd, this leaves exactly room for the single star. - Loop over the lines.
for (int i = 0; i < n; i++)runs once per line. - Build and print the line. Join the left spaces, the stars and the right spaces with
+, then print the result withConsole.WriteLine. The right-hand spaces are part of the line, and the statement requires them. - Update for the next line. If
i < n / 2, the rhombus is still widening: add 2 tostarsand subtract 1 fromspaces. Otherwise it narrows: subtract 2 fromstarsand add 1 tospaces. The middle line, wherei == n / 2, goes into theelsebranch, so the shrinking starts right after it. - Write
BuildString. It's apublicmethod that returns astringand takes anint nand achar character. - Fill it. Start from an empty string, loop
ntimes withstr += character;, and return the string.
The solution in C#
class Solution {
public string BuildString(int n, char character) {
string str = "";
for (int i = 0; i < n; i++) {
str += character;
}
return str;
}
public void PrintRhombus(int n) {
int stars = 1;
int spaces = n / 2;
for (int i = 0; i < n; i++) {
string str = BuildString(spaces, ' ') +
BuildString(stars, '*') +
BuildString(spaces, ' ');
Console.WriteLine(str);
if (i < n / 2) {
stars += 2;
spaces -= 1;
} else {
stars -= 2;
spaces += 1;
}
}
}
}
C# details worth noting:
charversusstring. The helper's parameter is achar, so the calls pass' 'and'*'with single quotes.string += charappends the character. The left side is a string, so the character is converted to text and joined. If you added twocharvalues together, you'd get anintinstead.- A statement can span lines. The expression for
strcontinues over three lines and ends only at the;. Putting the+at the end of a line is a common style. - The library shortcut.
new string(' ', spaces)does whatBuildStringdoes. Writing the helper yourself practises loops and string building. - Indentation doesn't matter. The compiler follows braces, so the lines of the multi-line expression can be indented any way.
Complexity
The output has n lines of n characters each, so O(n²) characters are produced no matter how they are built. This implementation does a little more work: += in BuildString copies the string every time, so building a run of k characters costs O(k²) character copies, and a line costs O(n²) in the worst case. The total is O(n³), which is fine for the small n in this lesson. Using new string(c, k) or a StringBuilder would bring it back down to O(n²). Extra space is O(n) for one line.
Edge cases and common mistakes
n = 1. The loop runs once, prints a single star with zero spaces on each side, and updates the variables, which are then never used.- Forgetting the right-hand spaces. The lines would be shorter than
ncharacters, and the output wouldn't match. - Using
i <= n / 2for the widening branch. The middle line would still widen, and the rhombus would continue growing for one extra line, so it would be too big. - Passing a string to the helper.
BuildString(2, " ")doesn't compile, because the second parameter is acharand needs single quotes. - Updating before printing. If the
if/elseblock ran first, the first line would already be a three-star line, and the output would be shifted by one line. - Even
n. The problem promises an odd number, because a symmetric pattern with one centre needs one.
Testing
n = 1prints*.n = 3prints*,***and*, each 3 characters wide.n = 5prints the five lines shown above.