Start learning free

LESSON 178 OF 348 · FUNCTIONS & CLASSES

Print Rhombus in TypeScript: Helper Methods and Loops

Practice O(n2) Read the full explanation

Given an odd positive integer n print a rhombus of stars as in the example below

Example:

Input: n = 5
Output:
  *  
 *** 
*****
 *** 
  *  

Explanation:
There are n = 5 lines. Each line contains exactly n = 5 characters.
1st line contains two spaces, one '*' and two spaces.
2nd line contains one space, three '*' and one space.
3rd line contains five stars.
4th line contains one space, three '*' and one space.
5th line contains two spaces, one '*' and two spaces.
Note: Be careful to add the necessary spaces at the end of every line!


STEP 1 OF 7
    Ctrl + Enter to check

    TYPESCRIPT · FUNCTIONS & CLASSES

    Print Rhombus in TypeScript, explained

    Problem overview

    The method printRhombus receives an odd positive integer n and prints a rhombus (a diamond) of stars. It prints n lines, and every line is exactly n characters wide, so the lines of stars are padded with spaces on both sides. The trailing spaces count: the line * has two spaces after the star.

    For n = 5 the output is the following. Here each space is shown as a dot so that you can see the padding:

    ..*..
    .***.
    *****
    .***.
    ..*..
    

    The widths of the star runs are 1, 3, 5, 3, 1. The padding on each side is 2, 1, 0, 1, 2.

    Approach: track two numbers per line

    Every line has the same shape: some spaces, some stars, the same number of spaces again. So a line is described by two numbers, stars and spaces (the padding on each side), and stars + 2 * spaces always equals n.

    The first line has one star and Math.floor(n / 2) spaces per side. In the top half, each line adds two stars and takes away one space on each side. After the middle line, each line does the opposite. The middle line is the widest, with n stars and no padding.

    Building a run of the same character many times is a job of its own, so the lesson pulls it out into a helper, buildString(n, character). The main method then reads almost like the shape: left padding, stars, right padding.

    Step by step

    The lesson writes printRhombus first, assuming the helper exists.

    1. Start with one star. Declare stars with let as a number, set to 1.
    2. Compute the padding. Declare spaces the same way, set to Math.floor(n / 2). For n = 5 the division gives 2.5 because / keeps the fraction, and Math.floor rounds it down to 2.
    3. Loop over the lines. Write for (let i = 0; i < n; i++), one pass per printed line.
    4. Build and print each line. Inside the loop, declare str as the left spaces, plus the stars, plus the right spaces, each made with this.buildString and joined with +. Print it with console.log. Both space runs are needed so that the line is exactly n characters long.
    5. Update for the next line. Still inside the loop, after printing, check i < Math.floor(n / 2). In the top half, add 2 to stars and subtract 1 from spaces. Otherwise, subtract 2 from stars and add 1 to spaces. The middle line, where i equals Math.floor(n / 2), takes the else branch, so the shape starts to narrow right after it.

    Then the helper, written above printRhombus inside the class:

    1. Declare it with parameters n: number and character: string, returning a string. TypeScript has no separate character type, so the character is a string of length one.
    2. Build the run. Declare str as an empty string, loop n times appending character with +=, and return str.

    The solution in TypeScript

    class Solution {
        buildString(n: number, character: string): string {
            let str: string = "";
            for (let i = 0; i < n; i++) {
                str += character;
            }
            return str;
        }
    
        printRhombus(n: number): void {
            let stars: number = 1;
            let spaces: number = Math.floor(n / 2);
            for (let i = 0; i < n; i++) {
                let str: string =
                    this.buildString(spaces, " ") +
                    this.buildString(stars, "*") +
                    this.buildString(spaces, " ");
                console.log(str);
                if (i < Math.floor(n / 2)) {
                    stars += 2;
                    spaces -= 1;
                } else {
                    stars -= 2;
                    spaces += 1;
                }
            }
        }
    }
    

    The TypeScript details worth a closer look:

    • Methods call each other through this. Inside printRhombus, a bare buildString(...) would not be found. this.buildString(...) calls the method on the same object.
    • The expression continues on the next line. The lines of the assignment end with +, so TypeScript knows the expression isn't finished. Putting the + at the start of the next line works too.
    • Two variables named str and i. The helper and the main method each have their own. Variables declared with let live only in the block or method where they appear, so they don't clash.
    • No integer division. number is a floating-point type, so 5 / 2 is 2.5. Math.floor(n / 2) gives the whole-number half. Without it, spaces would be 2.5 and the helper would run its loop three times for it.
    • "*" and " " are strings. Single and double quotes work the same, so ' ' and '*' are equally valid.
    • Built-in alternative. " ".repeat(spaces) does the job of buildString. The lesson writes the helper by hand to practise loops and methods.

    Complexity

    Time: O(n²). There are n lines, and each line is built in O(n) time, because the helper loops over a total of exactly n characters. The output itself has about n² characters, so no solution can be faster.

    Space: O(n). At any moment, the program holds one line of n characters, plus a few numbers.

    Edge cases and common mistakes

    • n = 1. One pass prints a single *. The values of stars and spaces after the update are not used.
    • n = 3. The output is .*., ***, .*., with dots standing for spaces.
    • Forgetting the right padding. The lines come out shorter than n, and the output no longer matches the expected text.
    • Updating before printing. The first line would already have three stars.
    • Using i <= Math.floor(n / 2) for the widening. The middle line would still widen the next line, which would get 7 stars when n is 5, more than the width.
    • Forgetting Math.floor. With fractional spaces the output for any odd n is wrong.
    • Even n. The statement promises an odd number. For an even one there is no single middle line, and this code would print a lopsided shape that is wider than n.

    Testing

    • n = 1 prints *.
    • n = 3 prints three lines: one star with a space on each side, then ***, then the first line again.
    • n = 5 prints the rhombus from the example, and each line is 5 characters long.
    Keep going with TypeScriptAbout 340 step-by-step lessons, from your first line of code to coding interviews. Free to start.
    Start learning free