NLP
Ruby programming
writing quality
text analysis
computational linguistics

NLP and Ruby to characterize quality of writing

ML System Design practice on Codemia

Design recommenders, ranking systems and training pipelines the way ML interviews actually ask for them, with worked solutions.

Practice ML system design

Introduction

Using NLP to characterize writing quality is possible, but it helps to define "quality" as measurable signals rather than as a single magic score. In practice, systems usually combine several features such as readability, grammar-error counts, lexical diversity, sentence length, and domain-specific style rules. Ruby can handle this kind of text analysis well, especially when you keep the pipeline simple and explicit.

Turn "quality" into measurable features

Before choosing tools, decide what you actually want to measure. Common signals include:

  • readability level
  • grammar or spelling errors
  • repetition and lexical diversity
  • sentence length and paragraph structure
  • tone consistency for a target audience

That is important because there is no universal NLP metric called "writing quality." A blog post, legal memo, and support email can all be "good" in different ways.

Start with tokenization and simple counts

Even basic text features can be useful. In Ruby, you can start with simple tokenization and sentence splitting:

ruby
1text = "Writing clearly matters. Short sentences are often easier to read."
2
3words = text.scan(/\b[\w']+\b/)
4sentences = text.split(/[.!?]+/).map(&:strip).reject(&:empty?)
5
6puts "word count: #{words.length}"
7puts "sentence count: #{sentences.length}"
8puts "average sentence length: #{words.length.to_f / sentences.length}"

That will not give you full NLP, but it does provide the foundation for readability and style heuristics.

Compute a few practical writing metrics

A simple heuristic pipeline might track:

  • average sentence length
  • average word length
  • vocabulary size
  • repeated words

Example:

ruby
1text = File.read("sample.txt")
2words = text.downcase.scan(/\b[\w']+\b/)
3sentences = text.split(/[.!?]+/).map(&:strip).reject(&:empty?)
4
5unique_words = words.uniq
6lexical_diversity = unique_words.length.to_f / [words.length, 1].max
7average_sentence_length = words.length.to_f / [sentences.length, 1].max
8average_word_length = words.sum(&:length).to_f / [words.length, 1].max
9
10puts "lexical diversity: #{lexical_diversity.round(3)}"
11puts "average sentence length: #{average_sentence_length.round(2)}"
12puts "average word length: #{average_word_length.round(2)}"

These are not final quality judgments, but they are useful features for scoring or flagging text for review.

Ruby works well as an orchestration layer

Ruby may not have the deepest NLP ecosystem compared with Python, but it works well for text preprocessing, heuristics, and service orchestration. A practical architecture is often:

  1. Ruby reads and normalizes the text
  2. Ruby computes simple metrics directly
  3. Ruby optionally calls an external NLP service or model for grammar, embeddings, or classification
  4. Ruby combines the results into a report

This is usually more maintainable than trying to invent a single all-knowing writing-quality formula inside one script.

Build a scoring approach that matches the use case

For example, a support-email quality checker might reward:

  • concise sentences
  • polite phrases
  • low grammar-error counts
  • presence of action-oriented language

A student-writing evaluator might care more about:

  • argument structure
  • vocabulary breadth
  • paragraph coherence
  • grammar patterns

The scoring rubric should come from the use case first, not from the toolchain.

Common Pitfalls

The most common mistake is treating writing quality as an objective single number. It is usually a collection of signals tied to a specific context.

Another common issue is overvaluing surface metrics. Longer words or bigger vocabulary do not automatically mean better writing.

People also build text scores without collecting examples of genuinely good and bad writing for their domain, which makes the metric arbitrary.

Finally, Ruby can orchestrate NLP work effectively, but if you need advanced pretrained models, you may want Ruby to call an external service or a separate model-serving layer rather than reimplement everything locally.

Summary

  • Writing quality is usually a combination of measurable signals, not one universal metric.
  • Ruby can compute useful text features such as sentence length, vocabulary diversity, and repetition.
  • Start with explicit heuristics before reaching for heavier NLP systems.
  • Match the scoring rubric to the kind of writing you actually care about.
  • Use Ruby as a practical analysis and orchestration layer rather than expecting one library to define quality for you.

Related reading
Free course
Beginner
7 lessons
2 hours
Tackling System Design Interview Problems

A short course that equips you with the skills to approach system design interviews methodically.

Start the free course
Track what you have practised

A free account saves your progress, solutions and study plan across every problem on Codemia.

ML System Design practice on Codemia

Design recommenders, ranking systems and training pipelines the way ML interviews actually ask for them, with worked solutions.

Practice ML system design

All Rights Reserved.