성능에 심각한 영향을 미치는 일반적인 Javascript 실수? [닫은]


10

최근에 참석 한 UI / UX MeetUp에서 상호 작용 및 UI에 Javascript (jQuery)를 사용하는 웹 사이트에 대한 피드백을 제공했습니다. 이는 매우 간단한 애니메이션 및 조작이지만 괜찮은 컴퓨터의 성능은 끔찍했습니다.

실제로 특정 문제가 성능을 절대적으로 파괴하는 동일한 문제로 본 많은 사이트 / 프로그램을 생각 나게했습니다. Javascript가 Flash 대체품으로 거의 사용되는 상황이 대부분입니다. 이것은 훨씬 더 많은 자바 스크립트와 기능을 가지고 있지만 매우 매끄럽게 실행되는 일부 웹 응용 프로그램과는 완전히 대조적입니다 (IBM의 COGNOS는 제가 생각할 수있는 것입니다).

JS를 개발할 때 고려되지 않은 일반적인 문제 중 일부를 알고 싶습니다. 사이트 성능을 저하시킵니다.


다른 모든 프로그램과 똑같이 : 필요 이상으로 많은 작업을 수행하고 동일한 작업을 반복하여 수백 번 반복합니다.

1
@delnan 그것은 매우 사실이지만 JS에서 훨씬 더 보편적 인 것처럼 보입니다. 아마도 인식?
Nic

1
JavaScript에 대해 이야기 할 때 '사이트'에 대해 이야기하는 것이 다소 지나가고 있습니다. 그것은 모든 곳에서 요즘 모든 것에 사용됩니다.
Adam Crossland

@Adam Crossland 당신은 절대적으로 맞습니다-같은 인스턴스에서 개발자에게 jQuery에 크게 의존하는 네이티브 앱을 도왔다 고 생각합니다.
Nic

1
귀하의 질문에 대한 정확한 대답은 아니므로, 나는 의견을 제시합니다 : JavaScript가 많은 렌더링을 한 상황을 경험했으며 실제로 브라우저의 렌더링 엔진이었습니다. 따라서 성능 병목 현상을 처리하기 위해 먼저 불필요한 렌더링 작업을 찾습니다.
user281377

답변:


8

일반적인 성능 킬러는 루프 .length내에서 HTMLCollection을 호출 for합니다.

function foo(collection) {
    for (var index = 0; index < collection.length; index++) {
        // do something awesome here
    }
}

안티 패턴은 루프를 통과 할 때마다 컬렉션의 크기가 계산되도록합니다. 더 나은 방법은 루프 외부의 길이를 계산하는 것입니다.

function foo(collection) {
    var collectionLen = collection.length;
    for (var index = 0; index < collectionLen; index++) {
        // do something awesome here
    }
}

3
브라우저에 따라 다릅니다. 이 가지고 벤치 마크를 예로 : 인 FF (5), "최적화 된"버전과 거의 같은 시간에 "정상"한 실행됩니다. 그리고 실제로 오래되고 느린 브라우저에서도 JS가 실제로 요소에 관심이있는 경우 이와 같은 것이 병목 현상이 발생하지 않을 것입니다.

1
흠! 아마도 오늘날의 고도로 최적화 된 JIT 컴파일러는 이러한 지혜를 쓸모 없게 만들고 있습니다.
Adam Crossland

4
나는 여기서 진정한 전문가는 아니지만 ECMA 사양에서 길이는 배열 객체의 속성 일뿐입니다. 따라서 호출하면 모든 요소를 ​​계산하는 대신 값을 반환합니다. 모든 구현이 사양을 따르는 지 모릅니다. 그러나 그렇게하면 코드의 성능이 전혀 향상되지 않습니다.
Jacek Prucia

4
@JacekPrucia 그는 배열이 아니라 컬렉션 이 아니라 실제 코드에서는 컬렉션 과 같은 함수에 의해 반환되는 DOM 요소의 목록을 의미한다고 말했다 . 이 함수는 속성에 액세스 할 때마다 길이를 다시 계산 하는 라이브 를 반환합니다 . document.getElementsByTagNamenodeList.length
Yi Jiang

2
@JacekPrucia 벤치 마크 는 성능 향상입니다. 부동산 조회는 저렴하지 않습니다.
Raynos

4

아니요, 플래시 교체로 사용 된 JS에서 문제가 발생하지 않습니다. 당신이 그것을 확신하지 못하면, 액션 스크립트에 대해 당신 자신을 문서화하십시오 : 그것은 JS에 매우 가깝습니다.

퍼포먼스 킬러로서 몇 가지 나쁜 습관을 찾을 수 있습니다.

  • 스크롤, 마우스 이동 또는 이와 유사한 것들과 같은 연속 이벤트에 이벤트 핸들러를 연결하십시오. 이벤트가 충분히 트리거되지 않으면 응용 프로그램이 반응하지 않습니다. 너무 많이 트리거되면 아무것도 CPU 부하가 커집니다.
  • 동기식 AJAX 호출 자바 스크립트는 멀티 스레딩되지 않으므로 JS의 일부가 무언가를 기다리는 경우 애플리케이션이 정지됩니다. 비동기 AJAX 호출을 사용하는 것이 좋으며 setTimeout / setInterval을 사용하여 긴 계산 단계를 분할하고 응용 프로그램을 반응 적으로 유지하는 것과 같은 방법입니다.
  • 다른 언어와 마찬가지로 알고리즘 복잡성이 높습니다.

플래시 교체 댓글 : 유래 어디 그 - 나는 회전, 쉽게, 또는 애니메이션 풀 브라우저 이미지를 시도하고 그 과정에서 비참하게 실패 할 몇 가지 더 애플 리케이션보다 더 본 적이

AJAX의 첫 번째 A는 비동기를 나타 내기 때문에 기술적으로 AJAX가 아니라면 동기가되지만 요점은 여전히 ​​좋은 것입니다.
Karl Bielefeldt

네, AJAX가 아닙니다. 그러나 어쨌든 이것은 피해야합니다 : D
deadalnix

3

상호 작용과 UI에 Javascript (jQuery)를 사용하는 웹 사이트에 대한 피드백을 제공했습니다. 상당히 간단한 애니메이션과 조작 이었지만 괜찮은 컴퓨터의 성능은 끔찍했습니다.

성능의 가장 큰 문제는 기본 DOM 모델과 CSS3 애니메이션 모델 (또는 캔버스 또는 svg)을 이해하지 않고 높은 수준의 추상화 (예 : jQuery)를 사용하는 것입니다.

당신이하지 않으면 추상적 개념없이 그것을 수행하는 방법 당신은 절대이 제로의 기술이 빠르게 또는 느리게 무엇인지에 대한 지식을.

JavaScript를 배우고 DOM을 배우십시오. 이 두 가지를 알고 추상화가 무엇을하는지 알면 효율적으로 사용할 수 있습니다. 물론 추상화를 깨닫는 대부분의 시간은 라이브러리없이 느리게하고 수동으로 수행하는 것입니다.


1

Javascript의 장점과 단점은 매우 유연하다는 것입니다. 즉, 실제로는 많은 경우에해서는 안되는 일을 할 수 있습니다.

내가 참여한 코드 검토에서 주요 관심사는 CSS 렌더링과 관련이있는 경향이 있습니다. 새로운 JS 개발자에게는 전역 범위에서 너무 많은 변수가 사용되는 경향이 있습니다.

또한 제대로 닫히지 않으면 메모리 누수가 발생할 수 있습니다. 그러나 대부분의 최신 Javascript 프레임 워크는 코드가 프레임 워크를 따르는 한 이러한 종류의 문제를 방지합니다.


0

더 나은 jquery 코드 작성에 대해 1 년 전에 찾은 빠른 링크는 다음과 같습니다. http://net.tutsplus.com/tutorials/javascript-ajax/10-ways-to-instantly-increase-your-jquery-performance /

성능을 저하시키는 동료 코드에서 내가 찾은 것 중 하나는 캐시 할 필요가없는 데이터를 캐싱하는 것입니다.

예:

var table = $("#data").dataTable(.....);

DataTables 는 멋진 그리드를 만드는 데 사용하는 jQuery 플러그인입니다. 어쨌든, 테이블에는 거의 5k 개의 행이있어 DataTables 플러그인을 적용한 다음 테이블 변수에 저장하면 실제로 FireFox와 IE는 스크립트가 너무 오래 걸렸다 고 경고했습니다. 이야기의 도덕은 필요한 경우에만 데이터를 캐시합니다.


1
DataTables가 캐싱 관련 문제가 아니라 실제로 비효율적이며 불량한 플러그인 인 것처럼 들립니다. 5k는 아무것도 아닙니다.
Raynos

@Raynos : 그는 5 킬로바이트의 데이터가 아니라 5k 개의 행을 말했다 . "행" 매우 큰 것일 있습니다.
크리스 파머

@ChrisFarmer "행"이 매우 큰 경우 다른 문제가 있습니다.
Raynos

-1

내가 들었던 것에서 for루프는 jQuery보다 계산 속도가 빠릅니다 $.each().


3
이것은 농담입니까?
Raynos
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.