PHP Descending Number Triangle Pattern (Right-Aligned)

Beginner
5 min read
Updated: Sep 2026
3 programs
Live preview

What Is This Pattern?

A right-aligned descending number triangle uses a fixed-width inner loop: print spaces while $j > $i, then digits $i..1 — so each row hugs the right edge.

Remember
Rule: for i from 1 to rows
        for j from rows down to 1
          if j > i: print space
          else: print j

    1
   21
  321
 4321
54321     ← rows = 5

Follows the spaced mirror in Program 29; next is the number-star diamond in Program 31.

How to Solve It

Outer loop grows $i. One fixed-width inner loop runs $rows..1 — print a space or a digit so columns stay aligned.

MethodIdeaBest for
Fixed-width if/else$j > $i → space; else print $jLearning, interviews, exams
Ternary formecho ($j > $i) ? " " : $j;Shorter demos once if/else is clear

Pseudocode

Pseudocode
for i from 1 to rows:
    for j from rows down to 1:
        if j > i: print space
        else: print j
    print newline

Cheat sheet

GoalPattern
Grow each rowfor ($i = 1; $i <= $rows; $i++)
Fixed widthfor ($j = $rows; $j >= 1; $j--)
Pad or digitif ($j > $i) echo " "; else echo $j;
Leading spaces$rows - $i spaces before digits
End of rowecho PHP_EOL;

Printing Numbers vs Starting a New Line

APIEffectUse for
echo $j / " "Stays on the same lineEach space or digit on the row
echo PHP_EOLEnds the current lineAfter the fixed-width loop finishes

Print characters without a newline, then end the row once.

Live Preview

Change the row count and the right-aligned triangle updates instantly — capped at 9 for readable demos.

Whole numbers from 1 to 9. Tap a chip or type a value — the preview redraws as you go.

Live result rows = 5 · 25 chars
    1
   21
  321
 4321
54321

Worked Walkthrough — $rows = 5

Trace how leading spaces shrink and descending digits grow on each row.

$iSpacesDigitsPrints
1411
232121
32321321
4143214321
505432154321

Leading spaces = $rows − $i. Each row prints $rows characters → O(n²) total.

PHP Programs

Three complete programs: fixed $rows = 5, CLI input with ternary form, and a compact $rows = 3 demo. Use View Output to reveal sample results.

Example 1 — Fixed $rows = 5

Hard-coded height — fixed-width descending loop with if/else for space vs digit.

PHP
<?php
for ($i = 1; $i <= 5; $i++) {
    for ($j = 5; $j >= 1; $j--) {
        if ($j > $i) {
            echo " ";
        } else {
            echo $j;
        }
    }
    echo PHP_EOL;
}
?>

How It Works

1. Outer grows the digit count. $i is how many digits appear on the right side of the row.

2. Fixed width. Inner loop always runs 5 times — unused left slots become spaces.

3. Descending digits. When $j <= $i, print $j so the filled part reads $i..1.

Example 2 — User Input Rows

Read $rows from the CLI, validate, then use a ternary for each position.

PHP
<?php
echo "Enter rows: ";
$input = trim(fgets(STDIN));

if (!is_numeric($input) || (int) $input <= 0) {
    echo "Please enter a positive integer." . PHP_EOL;
    exit(1);
}

$rows = (int) $input;

for ($i = 1; $i <= $rows; $i++) {
    for ($j = $rows; $j >= 1; $j--) {
        echo ($j > $i) ? " " : $j;
    }
    echo PHP_EOL;
}
?>

How It Works

1. Prompt and validate. Reject non-numeric and non-positive values before printing.

2. Same core. Ternary form matches Example 1’s if/else — only $rows comes from the user.

3. Safer input tip. Cap demos for readable output:

Safer input
if (!is_numeric($input) || (int) $input < 1 || (int) $input > 9) {
    echo "Enter a whole number from 1 to 9." . PHP_EOL;
    exit(1);
}

Example 3 — Compact $rows = 3

Same structure with only three rows — easy to confirm spaces shrink by one each time.

PHP
<?php
$rows = 3;

for ($i = 1; $i <= $rows; $i++) {
    for ($j = $rows; $j >= 1; $j--) {
        if ($j > $i) {
            echo " ";
        } else {
            echo $j;
        }
    }
    echo PHP_EOL;
}
?>

How It Works

1. Three rows. $i = 1 → 1; $i = 2 → 21; $i = 3 → 321.

2. Trace on paper. If the inner loop stops at $i instead of $rows, the triangle loses right alignment.

3. Scale up next. Once the small demo is clear, use Examples 1–2 for five rows or user input.

Edge Cases & Pitfalls

Check these before calling the solution done.

no spaces

Missing else for spaces

Skipping echo " " when $j > $i left-aligns the triangle — you get Program 3’s shape without padding.

width ≠ rows

Loop only to i

Inner loop must always run $rows times. Stopping at $i removes leading spaces and breaks alignment.

j++

Ascending inner loop

for ($j = 1; $j <= $rows; $j++) changes digit order and padding. Keep $j = $rows..1.

PHP_EOL inside

Broken rows

If echo PHP_EOL sits inside the inner loop, you get one character per line. Call it only after the loop.

rows = 1

Single digit

Output is just 1 with no leading spaces. A good sanity check for input validation.

fgets

Check is_numeric

Bare (int) casts turn non-numeric strings into 0 — prefer is_numeric before casting.

Time and Space Complexity

ProgramTimeExtra space
Fixed / input (Examples 1–2)O(n²)O(1)
Compact rows = 3 (Example 3)O(n²)O(1)

Each of n rows prints n characters → O(n²) time. Only a few loop variables are needed.

Key Takeaways

  • One fixed loop: $j = $rows..1 prints space when $j > $i, else digit $j.
  • Always width rows: fixed width is what keeps the triangle right-aligned.
  • Break the row: spaces and digits in the inner loop; echo PHP_EOL after it finishes.
  • Complexity: O(n²) time from n² characters; O(1) extra space.

One line: for each row $i, walk $j = $rows..1 and print space or $j, then echo PHP_EOL.

Frequently Asked Questions

A right-aligned descending triangle: for rows=5 you get 1 / 21 / 321 / 4321 / 54321 — leading spaces pad each row to width rows.
Leading spaces are printed while $j > $i. Smaller rows get more spaces, pushing digits to the right edge.
The inner loop runs $j from $rows down to 1. When $j <= $i, it prints $j — naturally producing $i..1 on each row.
Running $j from $rows down to 1 on every row keeps column alignment. Spaces fill positions where $j > $i.
Program 3 prints a left-aligned reverse descending triangle with no leading spaces. Program 30 pads with spaces for right alignment.
echo $j (or a space) stays on the same line. echo PHP_EOL ends the row after the fixed-width loop finishes.
Use trim(fgets(STDIN)) and check is_numeric($input) before casting to int — see Example 2.
O(n²) for n rows because each row runs a fixed-width inner loop of n iterations.

Did you know?

This pattern uses a fixed column width ($rows). For each row $i, the inner loop prints spaces while $j > $i, then prints digits in descending order — producing a right-aligned triangle.

Next: Number-Star Diamond Pattern

Continue with a diamond that mixes numbers and stars.

Program 31 tutorial →

About the author

Mari Selvan M P
Mari Selvan M P 🔗

Developer, cloud engineer, and technical writer

  • Experience 12 years building web and cloud systems
  • Focus Full Stack Development, AWS, and Developer Education

I write practical tutorials so students and working developers can learn by doing—from databases and APIs to deployment on AWS.

12 people found this page helpful