Text Justification

Last Updated : 3 Jul, 2026

Given an array of words words[] and a line width l, format the words such that each line has exactly l characters and is fully justified (both left and right).

  • Pack as many words as possible into each line greedily.
  • Distribute extra spaces as evenly as possible between words on each line.
  • If spaces cannot be distributed evenly, the left gaps get one more space than the right gaps.
  • The last line is left-justified with a single space between words and trailing spaces to fill the line.

Return a list of strings where each string represents one formatted line.

Examples:

Input: words[] = ["geeksforgeeks", "is", "the", "best", "computer", "science", "portal", "for", "geeks"], l = 16
Output: ["geeksforgeeks is", "the best", "computer science", "portal for geeks"]
Explanation:
"geeksforgeeks is": contains 13 and 2 characters separated by 1 space.
"the best": contains two words and 9 extra spaces.
"computer science": contains 8 and 7 characters and 1 extra space.
"portal for geeks": is left-justified with single spaces.

Input: words[] = ["geeks", "for", "geeks"], l = 8
Output: ["geeks ", "for ", "geeks "]
Explanation: Each line contains a single word, so the remaining positions are filled with trailing spaces.

Try It Yourself
redirect icon

Greedy Line Packing with Space Distribution - O(n × l) Time and O(n × l) Space

Pack as many words as possible into each line greedily, then distribute the remaining spaces mathematically. For a line with k words and g = k-1 gaps, compute spacePerGap = totalSpaces / g and extra = totalSpaces % g - the first extra gaps each get one more space than the rest. The last line is handled separately: single space between words, trailing spaces to fill.

C++
#include <vector>
#include <string>
#include <iostream>
using namespace std;

vector<string> justifyText(vector<string>& words, int l) {
    vector<string> result;
    int i = 0, n = words.size();
    while (i < n) {
        
        // Greedily pack words into the current line
        int lineLen = words[i].size();
        int j = i + 1;
        while (j < n && lineLen + 1 + (int)words[j].size() <= l) {
            lineLen += 1 + words[j].size();
            j++;
        }
        int numWords = j - i;
        int totalChars = 0;
        for (int k = i; k < j; k++) totalChars += words[k].size();
        int numSpaces = l - totalChars;
        string line = "";
        
        // Last line or single word: left justify with trailing spaces
        if (j == n || numWords == 1) {
            for (int k = i; k < j; k++) {
                if (k > i) line += " ";
                line += words[k];
            }
            line += string(l - line.size(), ' ');
        } else {
            
            // Distribute spaces evenly, left gaps get extra if uneven
            int gaps = numWords - 1;
            int spacePerGap = numSpaces / gaps;
            int extra = numSpaces % gaps;
            for (int k = i; k < j - 1; k++) {
                line += words[k];
                line += string(spacePerGap + (k - i < extra ? 1 : 0), ' ');
            }
            line += words[j - 1];
        }
        result.push_back(line);
        i = j;
    }
    return result;
}

int main() {
    vector<string> words = {"geeksforgeeks", "is", "the", "best", "computer",
                            "science", "portal", "for", "geeks"};
    int l = 16;
    vector<string> ans = justifyText(words, l);
    cout << "[";
    for (int i = 0; i < ans.size(); i++) {
        cout << "\"" << ans[i] << "\"";
        if (i != ans.size() - 1) cout << ", ";
    }
    cout << "]" << endl;
    return 0;
}
Java
import java.util.ArrayList;

class GFG {
    static ArrayList<String> justifyText(String[] words, int l) {
        ArrayList<String> result = new ArrayList<>();
        int i = 0, n = words.length;
        while (i < n) {

            // Greedily pack words into the current line
            int lineLen = words[i].length();
            int j = i + 1;
            while (j < n && lineLen + 1 + words[j].length() <= l) {
                lineLen += 1 + words[j].length();
                j++;
            }
            int numWords = j - i;
            int totalChars = 0;
            for (int k = i; k < j; k++) totalChars += words[k].length();
            int numSpaces = l - totalChars;
            StringBuilder line = new StringBuilder();

            // Last line or single word: left justify with trailing spaces
            if (j == n || numWords == 1) {
                for (int k = i; k < j; k++) {
                    if (k > i) line.append(" ");
                    line.append(words[k]);
                }
                while (line.length() < l) line.append(" ");
            } else {

                // Distribute spaces evenly, left gaps get extra if uneven
                int gaps = numWords - 1;
                int spacePerGap = numSpaces / gaps;
                int extra = numSpaces % gaps;
                for (int k = i; k < j - 1; k++) {
                    line.append(words[k]);
                    int sp = spacePerGap + (k - i < extra ? 1 : 0);
                    for (int s = 0; s < sp; s++) line.append(" ");
                }
                line.append(words[j - 1]);
            }
            result.add(line.toString());
            i = j;
        }
        return result;
    }

    public static void main(String[] args) {
        String[] words = {"geeksforgeeks", "is", "the", "best", "computer",
                          "science", "portal", "for", "geeks"};
        int l = 16;
        ArrayList<String> ans = justifyText(words, l);
        System.out.print("[");
        for (int i = 0; i < ans.size(); i++) {
            System.out.print("\"" + ans.get(i) + "\"");
            if (i!= ans.size() - 1) System.out.print(", ");
        }
        System.out.println("]");
    }
}
Python
def justifyText(words, l):
    result = []
    i = 0
    n = len(words)
    while i < n:

        # Greedily pack words into the current line
        lineLen = len(words[i])
        j = i + 1
        while j < n and lineLen + 1 + len(words[j]) <= l:
            lineLen += 1 + len(words[j])
            j += 1
        numWords = j - i
        totalChars = sum(len(words[k]) for k in range(i, j))
        numSpaces = l - totalChars
        line = ""

        # Last line or single word: left justify with trailing spaces
        if j == n or numWords == 1:
            line = " ".join(words[i:j])
            line += " " * (l - len(line))
        else:

            # Distribute spaces evenly, left gaps get extra if uneven
            gaps = numWords - 1
            spacePerGap = numSpaces // gaps
            extra = numSpaces % gaps
            for k in range(i, j - 1):
                line += words[k]
                line += " " * (spacePerGap + (1 if k - i < extra else 0))
            line += words[j - 1]
        result.append(line)
        i = j
    return result

if __name__ == "__main__":
    words = ["geeksforgeeks", "is", "the", "best", "computer",
             "science", "portal", "for", "geeks"]
    l = 16
    ans = justifyText(words, l)
    print("[" + ", ".join("\"" + s + "\"" for s in ans) + "]")
C#
using System;
using System.Collections.Generic;
using System.Text;

class GFG {
    static List<string> justifyText(string[] words, int l) {
        List<string> result = new List<string>();
        int i = 0, n = words.Length;
        while (i < n) {

            // Greedily pack words into the current line
            int lineLen = words[i].Length;
            int j = i + 1;
            while (j < n && lineLen + 1 + words[j].Length <= l) {
                lineLen += 1 + words[j].Length;
                j++;
            }
            int numWords = j - i;
            int totalChars = 0;
            for (int k = i; k < j; k++) totalChars += words[k].Length;
            int numSpaces = l - totalChars;
            StringBuilder line = new StringBuilder();

            // Last line or single word: left justify with trailing spaces
            if (j == n || numWords == 1) {
                for (int k = i; k < j; k++) {
                    if (k > i) line.Append(" ");
                    line.Append(words[k]);
                }
                while (line.Length < l) line.Append(" ");
            } else {

                // Distribute spaces evenly, left gaps get extra if uneven
                int gaps = numWords - 1;
                int spacePerGap = numSpaces / gaps;
                int extra = numSpaces % gaps;
                for (int k = i; k < j - 1; k++) {
                    line.Append(words[k]);
                    int sp = spacePerGap + (k - i < extra ? 1 : 0);
                    for (int s = 0; s < sp; s++) line.Append(" ");
                }
                line.Append(words[j - 1]);
            }
            result.Add(line.ToString());
            i = j;
        }
        return result;
    }

    static void Main() {
        string[] words = {"geeksforgeeks", "is", "the", "best", "computer",
                          "science", "portal", "for", "geeks"};
        int l = 16;
        List<string> ans = justifyText(words, l);
        Console.Write("[");
        for (int i = 0; i < ans.Count; i++) {
            Console.Write("\"" + ans[i] + "\"");
            if (i != ans.Count - 1) Console.Write(", ");
        }
        Console.WriteLine("]");
    }
}
JavaScript
function justifyText(words, l) {
    let result = [];
    let i = 0, n = words.length;
    while (i < n) {

        // Greedily pack words into the current line
        let lineLen = words[i].length;
        let j = i + 1;
        while (j < n && lineLen + 1 + words[j].length <= l) {
            lineLen += 1 + words[j].length;
            j++;
        }
        let numWords = j - i;
        let totalChars = 0;
        for (let k = i; k < j; k++) totalChars += words[k].length;
        let numSpaces = l - totalChars;
        let line = "";

        // Last line or single word: left justify with trailing spaces
        if (j === n || numWords === 1) {
            for (let k = i; k < j; k++) {
                if (k > i) line += " ";
                line += words[k];
            }
            while (line.length < l) line += " ";
        } else {

            // Distribute spaces evenly, left gaps get extra if uneven
            let gaps = numWords - 1;
            let spacePerGap = Math.floor(numSpaces / gaps);
            let extra = numSpaces % gaps;
            for (let k = i; k < j - 1; k++) {
                line += words[k];
                let sp = spacePerGap + (k - i < extra ? 1 : 0);
                for (let s = 0; s < sp; s++) line += " ";
            }
            line += words[j - 1];
        }
        result.push(line);
        i = j;
    }
    return result;
}

// driver code
let words = ["geeksforgeeks", "is", "the", "best", "computer",
             "science", "portal", "for", "geeks"];
let l = 16;
let ans = justifyText(words, l);
console.log("[" + ans.map(s => "\"" + s + "\"").join(", ") + "]");

Output
["geeksforgeeks is", "the         best", "computer science", "portal for geeks"]
Comment