将数组转换为字符串,使用分隔符分隔 - JavaScript

3

定义一个函数 myJoin,接受最多两个参数:

  1. array
  2. separator(字符串,可选)

myJoin 函数应返回一个字符串,其中包含数组中的所有元素连接在一起。分隔符应该用来分隔已连接的元素:

myJoin(['a', 'b', 'c'], '+'); // => "a+b+c"

如果未定义分隔符,则使用逗号','作为默认分隔符。
myJoin(['Peter', 'Paul', 'Mary']); // => "Peter,Paul,Mary"

如果数组中有任何元素是undefinednull,它们应该在返回的字符串中被替换为一个空字符串。

myJoin(['hello', undefined, 'world'], '-'); // => "hello--world"

我无法使用内置的 join 方法。

点此链接到 CodePen 进行测试

目前我已经尝试了:

function myJoin (array, separator) {

  let newString = "";

  if (separator = undefined) {
    separator === ",";
  }

  else {

    for (let i = 0; i < array.length; i++) {
      newString = i + separator;
    }

  }

  newString = array.toString();

  return newString;

}

console.log(myJoin(['a', 'b', 'c'], '+'));

^ 这不是将字符串的元素与分隔符组合在一起,而实际上返回了两次a,b,c。有任何想法吗?

编辑:在 @Jonas Wilms 的建议后,首次更新代码:

function myJoin (array, separator) {

  let newString = "";

  if (separator === undefined) {
    separator === ",";
  }

  for (let i = 0; i < array.length; i++) {
    newString += array[i] + separator;
  }

  return newString;

}

这在我的VS Code控制台中似乎可以工作,但在CodePen中无法工作。


你能解释一下你的代码吗? - PM 77-1
for 循环不应该在 else 子句中,而且 if 测试中的比较应该是 == 而不是 == 是用于 赋值)。 - Pointy
当然,我想说的是,如果定义了分隔符,就循环遍历数组以创建一个包含数组项(i)和分隔符的 newString。然后将 newString 转换为字符串并返回它。 - HappyHands31
1
代码 if (separator = undefined) 是将变量 separator 赋值为 undefined 值,而不是您期望的比较。 - Shidersz
7个回答

6
尝试
array.reduce( (s,x,i) => s+(i>0 ? separator : '') + (x==null ? '' : x), '') 

function myJoin(array, separator=',') { 
  return array.reduce( (s,x,i) => s+(i>0 ? separator : '') + (x==null ? '' : x), '') 
}

console.log( myJoin(['a', 'b', 'c'], '+') ); 
console.log( myJoin(['Peter', 'Paul', 'Mary']) );
console.log( myJoin(['hello', undefined, 'world'], '-') );

我们在这里使用标准的js功能:箭头函数, 数组reduce三元运算符。如果i>0(仅对第一个元素不成立),我们将分隔符添加到输出字符串s中。如果x未定义或空值,则我们将空字符串添加到s中 - 或在其他情况下添加x的值。

2
一些提示:
  • 不要混淆赋值运算符(=)和比较运算符(===)。if(a = b) 在99%的情况下都是错误的。

  • array.toString() 内部确实会调用 array.join(),我认为这是欺骗行为,而且我不确定你想要什么(我的意思是如果你正确地循环,newString 应该已经包含所需的结果了,不是吗?)

  • i 是你的 array 中获取该位置上的值的索引,请使用 array[i]

  • 我认为你的循环不应该在 else { 分支中,我认为你根本不需要那个 else(因为你总是想通过循环遍历数组来连接它)。

  • 使用 newString = 你重新分配了 newString 并且失去了之前的值,你可能想使用 newString += 来将一个值附加到它上面。

"Original Answer" 翻译成“最初的回答”。

请查看我的最新编辑 - 我尽可能地利用了你们的提示。 - HappyHands31
@happyHands31,你还需要在最后一个项目中添加分隔符,这样结果就是"a,b,c,"... - Jonas Wilms
那么我需要从返回的数组中删除最后一个项目吗?使用 .pop() 还是 .slice() - HappyHands31

2

使用模板字符串和mapforEach方法,如下所示:

function myJoin(arr, sep = ",") {
  arr = arr.map(e => [undefined, null].includes(e) ? "" : e);
  var result = "";
  arr.forEach((e, i) => result += `${i ? sep : ""}${e}`);
  return result;
}

console.log(myJoin(['Peter', undefined, 'Paul', null, 'Mary', 'Jack'], "-"));

ES5 语法:

function myJoin(arr, sep) {
  sep = sep || ",";
  arr = arr.map(function(e) {
    return [undefined, null].includes(e) ? "" : e;
  });
  var result = "";
  arr.forEach(function(e, i) {
    result += (i ? sep : "") + e;
  });
  return result;
}

console.log(myJoin(['Peter', undefined, 'Paul', null, 'Mary', 'Jack'], "-"));


1
Do not use the built-in .join array method in your answer. - Keith
已经修复了,@Keith。 - Jack Bashford

2

function myJoin(array, separator=',') {
  let str = '';
  for (let i = 0; i < array.length; i++) {
    if (array[i] !== null && array[i] !== undefined)
      str += array[i];
    if (i < array.length - 1)
      str += separator;
  }

  return str;
}

console.log(myJoin(['a','b','c']));
console.log(myJoin(['a','b','c'], '+'));
console.log(myJoin(['a',null,'c'], '-'));
console.log(myJoin(['a','b',undefined], '.'));


抱歉,我不理解...params作为参数的用法。您能否请使用我的代码中的参数arrayseparator来重新编写它? - HappyHands31
@HappyHands31...params接收所有的参数并将其组成一个数组。但是现在使用两个参数更容易理解了。 - David Alvarez
谢谢 - 是的,现在感觉清晰了,并且它有效。那么,您的两个“if语句”是在str中的array[i]separator之间进行交替添加?“if语句”默认就会交替附加它们吗? - HappyHands31
1
第一个 if 检查您的值是否应该附加到字符串中(不为 null 且不为 undefined)。第二个 if 检查如果我们在数组的最后一项,我们不会放置分隔符(避免在末尾有分隔符)。 - David Alvarez
1
"separator=','" 表示“默认值”。因此,如果您只提供一个参数,则分隔符将设置为“,”。如果您提供了两个参数,则“,”将被您的第二个参数覆盖。 - David Alvarez
显示剩余3条评论

2
使用默认语法设置分隔符为||。 使用forEach方法,传入参数valueindexarray。 测试最后一个元素。原始答案: "最初的回答"。

function myJoin (array, separator) {
  let newString = "";
  separator = separator||','; 
  
  array.forEach((a,i,arr) => {
    newString += `${a}${(i < arr.length-1) ? separator : ''}`;
  });
  return newString;
}

console.log(myJoin(['a', 'b', 'c'], '+'));
console.log(myJoin(['a', 'b', 'c']));
console.log(myJoin(['a', 'b', 'c'], '-'));


1
一个工作正常的代码为什么会被点踩而没有任何评论呢? - Bibberty

1
你可以使用 Array.reduce() 来连接你的数组。

let arr = ['a', 'b', undefined, 'c', 'd', null, 'e'];

myJoin = (arr, separator = ',') =>
  arr.reduce((acc, val, i) =>
    acc + ([undefined, null].indexOf(val) >= 0 ? '' : val) +
    (i < arr.length - 1 ? separator : ''), "");

console.log('myJoin(arr): ', myJoin(arr));
console.log('myJoin(arr, "+"): ', myJoin(arr, '+'));
console.log('arr.join("+"): ', arr.join('+'));

希望这有所帮助。

使用数组来检查一个值是否为 nullundefined 有点过度了,我认为 val == null 就足够了,因为 undefinednull 是松散相等的。 - customcommander
@customcommander 是的,我知道,可能现在只是习惯性的行为 :/ - Miroslav Glamuzina

1
一个人可以使用加入
let arr = [{id: 1, desc: 'desc1'}, {id: 2, desc: 'desc2'}];
let serialized = arr.map(x => JSON.stringify(x)).join('---');
console.log(serialized);

{"id":1,"desc":"desc1"}---{"id":2,"desc":"desc2"}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接