skip to Main Content

I am working on a functional programming exercise and I was asked to replace all whitespaces in the string with an hyphen. If I have a string like This is a title, the output should be this-is-a-title.

Now, all cases as described before work but I have an edge case string like this: Peter Is Coming. I would like to strip out the whitespace that is before the Coming so that my final output is peter-is-coming which would be the equivalent output for when I have an initial string of Peter is Coming with no redundant whitespace. I was able to do that of before Peter with ease using the trim method. How do I go about this edge case’s?

Note: One of the constraints is that there shouldn’t be the use of the replace method.

Thanks.

My code:

function urlSlug(title) {

  const url = title.trim().toLowerCase();
  console.log(url);

  const splitURL = url.split("");
  // console.log(splitURL);

  const urlArr = [];

  const filtered = splitURL.filter(val => {
    if (/s/.test(val)) {
      
      urlArr.push("-");
    }
    
    else {
      urlArr.push(val);
    }
  });

  return console.log(urlArr.join(""));

}

urlSlug("A Mind Needs Books Like A Sword Needs A Whetstone"); // a-mind-needs-books-like-a-sword-needs-a-whetstone
urlSlug("Hold The Door"); // hold-the-door 
urlSlug(" Peter is  Coming"); // peter-is--coming 

// The last output is what I get but not what I want to achieve.

3

Answers


  1. The condition if (/s/.test(val)) doesn’t consider consecutive whitespace characters between words.

    You can try the following way:

    function urlSlug(title) {
      //remove leading and trailing spaces
      //convert to lowercase
      const trimmedTitle = title.trim().toLowerCase();
    
      //split words array
      const words = trimmedTitle.split(/s+/);
    
      //join the words with hyphens
      const slug = words.join("-");
    
      return slug;
    }
    
    console.log(urlSlug("A Mind Needs Books Like A Sword Needs A Whetstone")); //a-mind-needs-books-like-a-sword-needs-a-whetstone
    console.log(urlSlug("Hold The Door")); //hold-the-door 
    console.log(urlSlug(" Peter is  Coming")); //peter-is-coming
    Login or Signup to reply.
  2. To solve this issue, you can use the split method to break the string into words, and then use join to concatenate them with hyphens. This way, redundant spaces are automatically removed.

        function urlSlug(title) {
          const url = title.trim().toLowerCase();
          const splitURL = url.split(/s+/);
          return splitURL.join("-");
        }
    
        console.log(urlSlug("A Mind Needs Books Like A Sword Needs A Whetstone")); // a-mind-needs-books-like-a-sword-needs-a-whetstone
    console.log(urlSlug("Hold The Door")); // hold-the-door
    console.log(urlSlug(" Peter is  Coming")); // peter-is-coming
    

    Here, /s+/ in the split function means that it will break the string at any amount of white space, thus removing redundant spaces. Then join concatenates the words with hyphens, solving your edge case.

    Login or Signup to reply.
  3. You can create a new variable previousWhiteSpace that keeps track of whether the previous iteration of .filter() resulted in whitespace.

    Using your current implementation, this doesn’t take much of a change (note previousWhiteSpace):

    function urlSlug(title) {
      const url = title.trim().toLowerCase();
      console.log(url);
    
      const splitURL = url.split("");
      // console.log(splitURL);
    
      const urlArr = [];
    
      let previousWhiteSpace = false;
    
      const filtered = splitURL.filter(val => {
        if (/s/.test(val)) {
          // after making sure val is whitespace, pass harmlessly if previous val was whitespace
          if (!previousWhiteSpace) {
            urlArr.push("-");
            previousWhiteSpace = true;
          }
        }
        else {
          urlArr.push(val);
          previousWhiteSpace = false;
        }
      });
    
      return console.log(urlArr.join(""));
    }
    
    urlSlug("A Mind Needs Books Like A Sword Needs A Whetstone"); // a-mind-needs-books-like-a-sword-needs-a-whetstone
    urlSlug("Hold The Door"); // hold-the-door 
    urlSlug(" Peter is  Coming"); // peter-is-coming 
    

    However, this can be vastly simplified by splitting url with a whitespace character (s) instead of "", saving you an extra iteration with filter.

    Example:

    function urlSlug(title) {
      const url = title.trim().toLowerCase();
    
      // whitespace regex to match every whitespace character
      const urlArr = url.split(/s+/);
    
      return console.log(urlArr.join("-"));
    }
    
    urlSlug("A Mind Needs Books Like A Sword Needs A Whetstone"); // a-mind-needs-books-like-a-sword-needs-a-whetstone
    urlSlug("Hold The Door"); // hold-the-door 
    urlSlug(" Peter is  Coming"); // peter-is-coming 
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search