singularize static method

String singularize(
  1. String word
)

Attempts to make a word singular using common English pluralization rules.

This is a basic implementation and may not handle all irregular plurals (e.g., 'children', 'mice') or complex cases perfectly. It includes specific exceptions for words like "address" or "status" that should not be changed, and words ending in "us", "ss", "is".

Rules applied:

  • ies -> y (e.g., stories -> story)
  • ches, shes, xes, zes -> remove es (e.g., boxes -> box)
  • s -> remove s (e.g., cats -> cat) - applied last.

Example:

StringUtils.singularize("stories") // "story"
StringUtils.singularize("boxes") // "box"
StringUtils.singularize("cats") // "cat"
StringUtils.singularize("status") // "status"

Implementation

static String singularize(String word) {
  if (word.isEmpty) {
    return word;
  }

  // Handle specific cases that shouldn't be singularized or have exceptions
  if (word.toLowerCase() == 'address' || word.toLowerCase() == 'status') {
    return word;
  }
  if (word.toLowerCase().endsWith('us') ||
      word.toLowerCase().endsWith('ss') ||
      word.toLowerCase().endsWith('is')) {
    // Avoid changing words like 'bus', 'address', 'analysis'
    return word;
  }

  // Rule: 'ies' -> 'y' (e.g., stories -> story)
  if (word.endsWith('ies')) {
    return '${word.substring(0, word.length - 3)}y';
  }

  // Rule: 'es' -> '' (e.g., boxes -> box, wishes -> wish)
  // Be careful not to remove 'es' if the singular ends in 'e' (e.g. 'addresses') - handled above
  if (word.endsWith('es')) {
    // Check for common cases like 'ches', 'shes', 'xes', 'zes'
    if (word.endsWith('ches') ||
        word.endsWith('shes') ||
        word.endsWith('xes') ||
        word.endsWith('zes')) {
      return word.substring(0, word.length - 2);
    }
    // Potentially other 'es' cases, but be cautious. For now, only handle the common ones.
    // If it ends in 'es' but not the above, maybe just remove 's'?
    // return word.substring(0, word.length - 1); // Alternative: just remove 's'
  }

  // Rule: 's' -> '' (e.g., cats -> cat)
  // This is the most basic rule, applied last.
  if (word.endsWith('s')) {
    return word.substring(0, word.length - 1);
  }

  // Add more rules here if needed (e.g., 'ves' -> 'f'/'fe')

  // Return original if no rule applies
  return word;
}