1

I am writing codes to convert initial letters of each word in a sentence to upper case and the rest to lower case. When I generated a new array arr and try to pass a number to it, there would be an error.

Cannot set property '0' of undefined.

I have no idea why this is happening.

function titleCase(str) {

  var word = str.split(" ");
  var arr = new Array();

  for(var i = 0; i<word.length; i++){
    arr[i][0] = word[i][0].toUpperCase();
    if(word[i].length>1)
    for(var j = 1; j<word[i].length; j++){
      arr[i][j] = word[i][j].toLowerCase();
    }
  }

  str = arr.join(' ');
  return str;
}

titleCase("I'm a little tea pot");

Thank you so much for your help!

Tasos K.
  • 7,979
  • 7
  • 39
  • 63
Ian Yang
  • 11
  • 1

5 Answers5

1

arr starts out as an empty array, but you try to reference (and change a property of) arr[i] without creating anything at arr[i] first:

arr[i][0] = word[i][0].toUpperCase();

To tweak your existing code, create an array inside the loop, change that array, then join it at the end and push to the outer arr:

function titleCase(str) {

  var word = str.split(" ");
  var arr = new Array();

  for (var i = 0; i < word.length; i++) {
    let newWordArr = [];
    newWordArr[0] = word[i][0].toUpperCase();
    if (word[i].length > 1) {
      for (var j = 1; j < word[i].length; j++) {
        newWordArr.push(word[i][j].toLowerCase());
      }
    }
    arr.push(newWordArr.join(''));
  }

  str = arr.join(' ');
  return str;
}

console.log(titleCase("I'm a little tea pot"));

But I'd suggest using a regular expression instead: put the first non-space character into a capture group, while putting following non-space characters into a different capture group, then .replace with the first group .toUpperCase() and the second group .toLowerCase():

const titleCase = str => str
  .replace(
    /(\S)(\S*)/g,
    (_, g1, g2) => g1.toUpperCase() + g2.toLowerCase()
  );

console.log(titleCase("I'm a little tea pot"));

(\S) - Match and capture a single non-space character (goes into argument g1 above)

(\S*) - Match and capture zero or more non-space characters that follow (goes into argument g2 above)

CertainPerformance
  • 356,069
  • 52
  • 309
  • 320
1
function titleCase(str) {

  var word = str.split(" ");
  var arr = new Array();

  for(var i = 0; i<word.length; i++){
    let newWord = '';
    for(var j = 0; j < word[i].length; j++){
      if(j === 0){
        newWord += word[i][j].toUpperCase();

      }
      else {
        newWord += word[i][j].toLowerCase();
      }
    }
    arr.push(newWord);
  }

  str = arr.join(' ');
  return str;
}

console.log(titleCase("I'm a little tea pot"));
Faisal Rashid
  • 368
  • 1
  • 11
0

Javascript only has 1-dimensional arrays, but you can build arrays of arrays...

here

titleCase("I'm a little tea pot");

function titleCase(str) {

  var word = str.split(" ");
  var arr = new Array();

  var arr = []
  for (var i=0;i<word.length;i++) {
     arr[i] = [];
  }

  for(var i = 0; i<word.length; i++){
    arr[i][0] = word[i][0].toUpperCase();
    if(word[i].length>1)
    for(var j = 1; j<word[i].length; j++){
      arr[i][j] = word[i][j].toLowerCase();
    }
  }

  str = arr.join(' ');
  return str;
}

console.log (titleCase("I'm a little tea pot"));
Schmuhl
  • 11
  • 4
0

You need to just show this title in your style(uppercase letter in each word), you can do this by using following methods:

  1. You can simply archive that by using css.

#title {
  text-transform: capitalize;
}
<span id="title">I'm a little tea pot</span>
  1. If you want to get this result with javascript, you need to do DOM operation.

document.getElementById('title').style.textTransform = 'capitalize';
<span id="title">I'm a little tea pot</span>
Diamond
  • 3,470
  • 2
  • 19
  • 39
0

According to your error.

Cannot set property '0' of undefined.

This error is occurred at arr[i][0] = word[i][0].toUpperCase(), because arr[i]is undefined as you can see in my snippet.

So you need to add a new item into arr array by using arr.push() like below;

function titleCase(str) {

  var word = str.split(" ");
  var arr = new Array();

  for(var i = 0; i<word.length; i++){
    console.log(`arr[${i}] is ${arr[i]}`);
    arr.push(word[i][0].toUpperCase());
    if(word[i].length>1) {
      arr[i] = `${arr[i]}${word[i].slice(1)}`;
    }
  }

  console.log(arr);
  
  return arr.join(' ');
}

console.log(titleCase("I'm a little tea pot"));
Diamond
  • 3,470
  • 2
  • 19
  • 39