admin管理员组

文章数量:1208155

How can I replace first N occurrences of many whitespaces and tabs in the following string:

07/12/2017  11:01 AM             21523 filename with s p a c  e  s.js

I am expecting the following result:

07/12/2017|11:01|AM|21523|filename with s p a c  e  s.js

I know not very elegant option only via calling replace N times on the same string

.replace(/\s+/, "|").replace(/\s+/, "|").replace(/\s+/, "|");

Worth to mention that I'm going to run this on near 1,000,000 lines so performance matters.

How can I replace first N occurrences of many whitespaces and tabs in the following string:

07/12/2017  11:01 AM             21523 filename with s p a c  e  s.js

I am expecting the following result:

07/12/2017|11:01|AM|21523|filename with s p a c  e  s.js

I know not very elegant option only via calling replace N times on the same string

.replace(/\s+/, "|").replace(/\s+/, "|").replace(/\s+/, "|");

Worth to mention that I'm going to run this on near 1,000,000 lines so performance matters.

Share Improve this question edited Nov 10, 2017 at 20:28 Systems Rebooter asked Nov 10, 2017 at 20:17 Systems RebooterSystems Rebooter 1,3993 gold badges18 silver badges32 bronze badges 3
  • 1 @stealththeninja Op wants to only replace the first 4 occurrences in the strings, thus leaving the spaces in the file name intact. – Derek 朕會功夫 Commented Nov 10, 2017 at 20:20
  • g will replace everything. But i need to replace only first n occurrences – Systems Rebooter Commented Nov 10, 2017 at 20:21
  • smells like you can use a loop of some sort – Namaskar Commented Nov 10, 2017 at 20:23
Add a comment  | 

7 Answers 7

Reset to default 9

Probably something like this:

var txt = "07/12/2017  11:01 AM             21523 filename with s p a c  e  s.js";

var n = 0, N = 4;
newTxt = txt.replace(/\s+/g, match => n++ < N ? "|" : match);

newTxt; // "07/12/2017|11:01|AM|21523|filename with s p a c  e  s.js"

You could take a counter and decrement it.

var string = '07/12/2017  11:01 AM             21523 filename with s p a c  e  s.js',
    n = 4,
    result = string.replace(/\s+/g, s => n ? (n--, '|') : s);
    
console.log(result);

You could replace the ternary expression with one with logical AND and OR.

var string = '07/12/2017  11:01 AM             21523 filename with s p a c  e  s.js',
    n = 4,
    result = string.replace(/\s+/g, s => n && n-- && '|' || s);
    
console.log(result);

Derek and Nina provide great answers for dynamically replacing N whitespace groups. If N is static, the non-whitespace token (\S) can be used to match and keep the groups between whitespace:

.replace(/\s+(\S+)\s+(\S+)\s+/, '|$1|$2|')

Some answers here are really good already, but since you say you want speed, I'd go with a single while, like this:

var logLine = '07/12/2017  11:01 AM             21523 filename with s p a c  e  s.js';
var N = 4;
while(--N + 1){
  logLine = logLine.replace(/\s+/, '|');
}
console.log(logLine);

Here's on JSFiddle: https://jsfiddle.net/2bxpygjr/

I'd go with something like this. Though I kinda like Derek's answer so I'll look his up and understand what he/she does in it.

var mytext = "some text separated by spaces and spaces and more spaces";
var iterationCount = 4;
while(iterationCount > 0)
  {
    mytext = mytext.replace(" ", "");
    iterationCount--;
  }
return mytext;

What about recursive version of you own solution?

function repalceLeadSpaces(str, substitution, n) {
    n = n || 0;
    if (!str || n <= 0) {
        return str;
    }
    str = str.replace(/\s+/, substitution);
    return n === 1 ? str : repalceLeadSpaces(str, substitution, n - 1)
}

You could also:

  • split on whitespace, using a capturing group to retain the spacing;
  • use map to replace the first N whitespace elements with |;
  • join the parts back together

const str = '07/12/2017  11:01 AM             21523 filename with s p a c  e  s.js'

const N = 4
const result = str.split(/(\s+)/).map((v, i) => i % 2 == 0 || i >= 2*N ? v : '|').join('')

console.log(result)

本文标签: javascriptReplace First N Occurrences in the StringStack Overflow