Gunning Fog Index

The Gunning Fog Index, published by Robert Gunning in 1952, estimates how hard a passage is to read from two signals: long sentences and long words. This page breaks the formula into steps, explains the heuristics in the code below, shows a more robust implementation, and describes where readability scores are useful in search and RAG systems.

The Gunning Fog Index is a readability test that estimates the years of formal education needed to understand a text on the first reading. It takes into account the number of words, the number of complex words (words with three or more syllables), and the number of sentences in a text.
import re

def count_words(text):
    """Counts the number of words in a text."""
    words = re.findall(r'\w+', text)
    return len(words)

def count_sentences(text):
    """Counts the number of sentences in a text."""
    sentences = re.split(r'[.!?]+', text)
    return len(sentences) - 1 if text[-1] in '.!?' else len(sentences)

def count_complex_words(text):
    """Counts the number of complex words in a text (words with three or more syllables)."""
    def syllable_count(word):
        word = word.lower()
        vowels = "aeiouy"
        count = 0
        if word[0] in vowels:
            count += 1
        for index in range(1, len(word)):
            if word[index] in vowels and word[index - 1] not in vowels:
                count += 1
        if word.endswith("e"):
            count -= 1
        if count == 0:
            count += 1
        return count

    words = re.findall(r'\w+', text)
    complex_words = [word for word in words if syllable_count(word) >= 3]
    return len(complex_words)

def gunning_fog_index(text):
    """Calculates the Gunning Fog Index for a given text."""
    num_words = count_words(text)
    num_sentences = count_sentences(text)
    num_complex_words = count_complex_words(text)

    if num_sentences == 0:
        return 0  # Avoid division by zero

    average_sentence_length = num_words / num_sentences
    percentage_complex_words = (num_complex_words / num_words) * 100

    fog_index = 0.4 * (average_sentence_length + percentage_complex_words)
    return fog_index

# Example usage
text = (
    "The Gunning Fog Index is a readability test for English writing. "
    "It estimates the years of formal education needed to understand the text on the first reading. "
    "Complex words are those with three or more syllables."
)

fog_index = gunning_fog_index(text)
print(f"The Gunning Fog Index for the given text is: {fog_index:.2f}")

OUTPUT

The Gunning Fog Index for the given text is: 10.40

Gunning Fog Index Explanation

The Gunning Fog Index is a readability test that estimates the years of formal education needed to understand a text on the first reading. The implementation calculates the Gunning Fog Index using the following steps:

  1. Words:
  2. Sentences:
  3. Complex Words:
  4. Gunning Fog Index Calculation:

Usage:

This implementation provides a way to rank texts based on readability using the Gunning Fog Index, which is useful in various Natural Language Processing (NLP) applications such as document analysis, content creation, and education.


1. The formula step by step

Computing the Gunning Fog Index Text Count words W Count sentences S Complex words 3+ syllables, C 0.4(W/S + 100C/W) grade level

The index is 0.4 x (average sentence length + percentage of complex words). Average sentence length is words divided by sentences. A complex word has three or more syllables; Gunning's original guidance excludes proper nouns, familiar compound words, and words that only reach three syllables through common suffixes such as -es, -ed or -ing. Most software implementations, including the one on this page, skip those exclusions and simply count syllables, which tends to push scores slightly higher.

Example: a 100-word passage with 5 sentences and 12 complex words gives 0.4 x (20 + 12) = 12.8, roughly the reading level of a high-school senior.

2. Interpreting scores

Interpreting the score 6 to 8 plain English 10 to 12 general public limit 13 to 16 college level 17+ graduate / dense The score approximates US school grade years needed on first reading.

Popular newspapers and consumer documentation usually aim for 8 to 12. Technical documentation and legal text commonly score 15 or more. The score measures surface features only: a short, simple-word sentence about an unfamiliar concept can score low and still be hard to understand, and the index says nothing about structure, jargon that happens to be short, or correctness.

3. A more robust implementation

The sample code counts syllables by counting vowel groups and subtracting a trailing e. That heuristic is reasonable but miscounts words like table (it returns 1). Using a pronunciation dictionary where available and a heuristic as fallback improves accuracy:

import re

try:
    import pyphen                     # pip install pyphen (hyphenation dictionaries)
    _dic = pyphen.Pyphen(lang="en_US")
    def syllables(w):
        return max(1, len(_dic.inserted(w).split("-")))
except ImportError:
    def syllables(w):
        w = w.lower()
        groups = re.findall(r"[aeiouy]+", w)
        n = len(groups)
        if w.endswith("e") and not w.endswith("le") and n > 1:
            n -= 1
        return max(1, n)

def gunning_fog(text: str) -> float:
    sentences = [s for s in re.split(r"[.!?]+\s*", text) if s.strip()]
    words = re.findall(r"[A-Za-z]+(?:'[a-z]+)?", text)
    if not sentences or not words:
        return 0.0
    complex_ = [w for w in words
                if syllables(w) >= 3 and not w[0].isupper()
                and not re.search(r"(es|ed|ing)$", w)]
    return 0.4 * (len(words) / len(sentences) + 100 * len(complex_) / len(words))

print(round(gunning_fog("The cat sat on the mat. It was happy."), 1))
print(round(gunning_fog("Organizational interoperability necessitates comprehensive documentation."), 1))

The textstat package provides textstat.gunning_fog() along with Flesch, SMOG and other indices if you prefer a maintained library.

4. Comparison with other readability metrics

MetricInputsOutput
Gunning FogSentence length, 3+ syllable wordsGrade level
Flesch Reading EaseSentence length, syllables per word0 to 100, higher is easier
Flesch-Kincaid GradeSame as FleschGrade level
SMOGPolysyllables in 30 sentencesGrade level, used in health literature
Coleman-LiauCharacters per wordGrade level, no syllable counting

5. Uses in search and RAG

In retrieval systems readability scores are cheap features. They can flag boilerplate or garbled extraction (OCR noise produces extreme scores), help route queries to simpler or more technical sources, or check that generated answers meet a target reading level for a patient-facing or customer-facing product. They should be a filter or a ranking signal among many, never the only judge of quality.

6. Pitfalls