소위 숫자 형태는 단일 자릿수에서 시작하여 세 자릿수 사이에 쉼표를 추가하는 것입니다. 예를 들어, "10,000". 이 요구 사항을 해결하기 위해 처음에는 다음과 같은 기능을 썼습니다.
코드 사본은 다음과 같습니다.
// 메소드 1
기능 tothens (num) {
var result = [], 카운터 = 0;
num = (num || 0) .toString (). split ( '');
for (var i = num.length-1; i> = 0; i-) {
카운터 ++;
result.unshift (num [i]);
if (! (counter % 3) && i! = 0) {result.unshift ( ','); }
}
return result.join ( '');
}
메소드의 실행 프로세스는 숫자를 문자열로 변환하고 배열로 나눈 다음 끝에서 시작하여 배열의 요소를 새 배열의 시작 부분 (결과)에 삽입하는 것입니다. 요소가 삽입 될 때마다 카운터는 숫자를 계산합니다 (추가 1). 카운터가 3의 배수 인 경우 쉼표가 삽입되지만 처음에는 쉼표가 필요하지 않도록주의하십시오 (0 일 때). 마지막으로, 결과는 새 배열의 JIN 메소드를 호출하여 얻습니다.
이 방법은 명확하고 이해하기 쉬웠으며 프로젝트에서 한동안 사용되었습니다. 그러나 직관은 그것이 잘 작동하지 않는다고 말합니다.
방법 2- 방법 1의 문자열 버전
코드 사본은 다음과 같습니다.
// 방법 2
기능 tothens (num) {
var result = '', counter = 0;
num = (num || 0) .toString ();
for (var i = num.length-1; i> = 0; i-) {
카운터 ++;
결과 = num.charat (i) + 결과;
if (! (counter % 3) && i! = 0) {result = ',' + result; }
}
반환 결과;
}
방법 2는 방법 1의 개선 된 버전입니다. 문자열을 배열로 나누지 않으며 항상 문자열에서 작동합니다.
메소드 3- 루프는 끝에서 세 숫자와 일치합니다.
코드 사본은 다음과 같습니다.
// 방법 3
기능 tothens (num) {
var num = (num || 0) .toString (), re = // d {3} $/, result = '';
while (re.test (num)) {
결과 = regexp.lastmatch + 결과;
if (num! == regexp.lastmatch) {
결과 = ',' + 결과;
num = regexp.leftContext;
} 또 다른 {
num = '';
부서지다;
}
}
if (num) {result = num + result; }
반환 결과;
}
방법 3은 완전히 다른 알고리즘입니다. 끝의 세 숫자는 정규식 루프를 통해 일치합니다. 경기가 일치 할 때마다 쉼표와 일치하는 컨텐츠는 결과 문자열의 시작 부분에 삽입되며, 일치하는 대상 (NUM)이 아직 일치하지 않은 컨텐츠 (regexp.leftContext)에 할당됩니다. 또한 참고 사항 :
1. 자리 수가 3의 배수 인 경우 마지막 일치는 3 개의 숫자 여야하지만 처음 세 숫자 전에 쉼표를 추가 할 필요가 없습니다.
2. 숫자의 비트 수가 3의 배수가 아닌 경우, NUM 변수에는 결국 1 ~ 2 개의 숫자가 남아 있습니다. 루프 후 나머지 숫자는 결과 문자열의 시작 부분에 삽입되어야합니다.
방법 3은 루프 수를 줄이지 만 (한 번에 3 개의 문자가 처리 됨), 정규 표현식의 사용으로 인해 소비량이 어느 정도 증가합니다.
방법 4- 방법 3의 문자열 버전
코드 사본은 다음과 같습니다.
// 메소드 4
기능 tothens (num) {
var num = (num || 0) .toString (), result = '';
while (num.length> 3) {
결과 = ',' + num.slice (-3) + 결과;
num = num.slice (0, num.length -3);
}
if (num) {result = num + result; }
반환 결과;
}
실제로, 마지막 세 문자를 가로 채는 기능은 문자열 유형의 슬라이스, 서브 스트링 또는 서브 스트링 방법을 통해 달성 될 수 있습니다. 이것은 정규 표현을 피합니다.
방법 5- 조합 및 수렴 방법
코드 사본은 다음과 같습니다.
// 메소드 5
기능 tothens (num) {
var num = (num || 0) .toString (), temp = num.length % 3;
스위치 (온도) {
case 1:
num = '00' + num;
부서지다;
case 2:
num = '0' + num;
부서지다;
}
num.match (// d {3}/g) .join ( ','). 대체 (/^0+/, '');
}
먼저, 숫자 수를 3의 배수로 구성하고 정규 표현식을 통해 3 개의 숫자마다 그룹으로 자른 다음 조인 방법을 통해 쉼표를 추가 한 다음 최종적으로 보완 0을 제거하십시오.
방법 6- 게으른 방법
코드 사본은 다음과 같습니다.
// 메소드 6
기능 tothens (num) {
return (num || 0) .toString (). 교체 (/(/d) (? = (? :/d {3})+$)/g, '$ 1,');
}
나는 항상이 형식이 정규 표현식 교체로 만들어 질 수 있다고 생각하지만 어설 션 및 기타 작문 방법을 사용해야하지만이 부분에 익숙하지 않습니다. Googled 이후, 나는 그러한 정규 표현식을 발견했는데, 아마도 코드의 가장 짧은 구현 일 것입니다.
테스트 결과
| 숫자 | 5000 번 (MS)에 소요되는 시간 | |||||
|---|---|---|---|---|---|---|
| 방법 1 | 방법 2 | 방법 3 | 방법 4 | 방법 5 | 방법 6 | |
| 1 | 4 | 1 | 3 | 1 | 14 | 2 |
| 10 | 14 | 1 | 3 | 0 | 7 | 2 |
| 100 | 12 | 1 | 2 | 4 | 5 | 3 |
| 1000 | 13 | 2 | 3 | 2 | 9 | 5 |
| 10000 | 스물 하나 | 4 | 3 | 1 | 6 | 3 |
| 100000 | 스물 하나 | 3 | 2 | 1 | 5 | 6 |
방법 1과 방법 2 사이의 강력한 비교는 문자열 작업의 효율이 배열 작업의 효율보다 훨씬 높다는 것을 보여줍니다. 방법 6의 테스트 결과는 코드의 길이가 성능과 관련이 없음을 알려줍니다. 방법 4는 최상의 포괄적 인 성능을 가지고 있지만 (100 num이 실제로 해결할 수없는 경우 NUM이 감소합니까?) 주된 이유는 다음과 같습니다.
1. 방법 1과 2를 비교하고 루프 수를 줄이기 위해 매번 1 문자 대신 3자를 작동하십시오.
2. 정규 표현을 사용하지 않고 소비를 줄이지 않고 비교 방법 3, 5 및 6.
마지막으로, 메소드 4를 최종 최적화 솔루션으로 선택했습니다. 독자는 더 나은 구현 방법이나 제안이 있는지 언급 할 수 있습니다.