DEV Community

Discussion on: Capitalize the first letter of every word

Collapse
 
aminnairi profile image
Amin • Edited

Hi there, very nice use of the String & Array prototypes chains. Thanks for your solution.

If I may, I would like to suggest another alternative involving less time complexity and using a sentinel value for detecting spaces. Because using split and map and join means many loops through the strings and array items generated.

The following algorithm can reduce the time complexity to O(n), n being the number of characters in the text.

"use strict";

const capitalize = (text) => {
    let isPreviousLetterSpace = true;
    let capitalized = "";

    for (const letter of text) {
        if (isPreviousLetterSpace) {
            isPreviousLetterSpace = false;
            capitalized += letter.toUpperCase();
            continue;
        }

        if (letter === " ") {
            isPreviousLetterSpace = true;
            capitalized += letter;
            continue;
        }

        capitalized += letter.toLowerCase();
    }

    return capitalized;
};

const text = "hello world";
const capitalized = capitalize(text);

console.log(capitalized); // "Hello World"

I also run some performance tests to see the outcome and it seems like the solution you provided is around 40 to 50% slower than the one I provided. So performance in the case of capitalizing hundreds or thousands of strings should be taken into account I guess. It was tested on Google Chrome and may vary from a browser to another.

What do you think about it?

Just for the record: I'm not saying that your solution is wrong. In the contrary, I think that solution you provided is the best because it involves less complexity to find the perfect algorithm to solve the task and premature optimizations like I just did should never happen unless you have a very good reason to. What I showed is only for finding an alternative solution and discuss about it.

Also, you made a very minor typo by writing capitlize instead of capitalize for the name of the function. But that's okay.

Again, very good work mate!

Collapse
 
alexanderjanke profile image
Alex Janke

Just on my phone right now but "split map join" in your perf-url is constantly 20-40% faster than the for loop version. I've done like 20 iterations now and number 2 is always faster (at least for me)

Collapse
 
ml318097 profile image
Mehul Lakhanpal

Lol. I made 2 typos actually. Got to know it now ๐Ÿ˜‚๐Ÿ˜‚ thanks though..๐Ÿ‘๐Ÿ˜€

Collapse
 
ml318097 profile image
Mehul Lakhanpal

Sure, there are tradeoffs with every solution.

Collapse
 
anders profile image
Anders

This looks like a better version from a performance perspective for sure, I did this implementation of the same

function captilizeAllWords(s) {

  var capitalize = true;
  var returnValue = '';

  for (var i = 0; i < s.length; ++i) {

    var c = s[i];

    if (c == ' ') { 

      capitalize = true; 

    } else if (capitalize) {

      c = c.toUpperCase();
      capitalize = false;
    }

    returnValue += c;
  }

  return returnValue;
}

In an article I wrote here a few days ago: dev.to/anders/why-do-we-write-java...

Given that "of" seems like it may be a little slow this is probably even faster.

Collapse
 
euantorano profile image
Euan T

Another alternative would be using a regular expression, which is quite nice and compact:

function capitalize(text) {
  return text.replace(/(^[a-z]| [a-z])/g, function (match, letter) {    
    return letter.toUpperCase();
  });
}

const text = "hello world";
const capitalized = capitalize(text);

console.log(capitalized); // "Hello World"

This also turns out to be even faster in my benchmarks - this will be due to the regular expression engine being highly optimised and built into the browser. My results from the perf.link site (which doesn't seem to want to let me copy a link directly to the benchmark for some reason...) are as follows:

function ops/s %
regexCapitalize 446,440 100%
capitalize2 184,960 41%
capitalize 144,600 32%
Collapse
 
ml318097 profile image
Mehul Lakhanpal

That's awesome. Hell lot of difference๐Ÿ”ฅ