source

malloc() 통화량을 최소화하면 성능이 향상됩니까?

manysource 2023. 11. 6. 21:55

malloc() 통화량을 최소화하면 성능이 향상됩니까?

malloc()를 여러 번 호출하는 (1번) 애플리케이션과 malloc()를 몇 번 호출하는 (2번) 애플리케이션을 생각해 보십시오.두 응용 프로그램 모두 동일한 양의 메모리를 할당합니다(100MB로 가정).
다음 malloc() 호출은 #1과 #2 중 어느 애플리케이션에서 더 빠를까요?
즉,malloc()는 메모리에 할당된 위치의 인덱스를 가지고 있습니까?

당신은 두가지 질문을 했습니다.

  • 다음 malloc () 호출은 1번과 2번 중 어느 애플리케이션에서 더 빠를까요?
  • 즉,malloc()는 메모리에 할당된 위치의 인덱스를 가지고 있습니까?

당신은 그들이 같은 질문이라고 암시했지만, 그렇지 않습니다.후자의 질문에 대한 답은 YES입니다.

어느 쪽이 더 빠를지에 대해서는 말할 수 없습니다.할당기 알고리즘, 기계 상태, 현재 프로세스의 단편화 등에 따라 달라집니다.

그러나 당신의 생각은 건전합니다. 당신은 매크로 사용이 성능에 어떤 영향을 미칠지 생각해 보아야 합니다.예전에 제가 쓴 앱 중에 malloc()로 할당된 메모리를 많이 사용하는 앱이 있었습니다.제대로 작동은 했지만 속도는 느렸습니다.malloc에 걸려오는 수많은 호출을 단 하나로 바꾼 다음, 제 앱에서 그 큰 블록을 잘라냈습니다.훨씬 더 빨랐습니다.

이 방법은 권장하지 않습니다. 단지 몰로크 사용이 성능에 중요한 영향을 미칠 수 있다는 점을 보여주는 것일 뿐입니다.

조언은 치수를 재라는 것입니다.

물론 이는 malloc 구현에 전적으로 달려 있지만, 이 경우 무료 통화가 없는 대부분의 malloc 구현은 아마도 동일한 알고리즘 속도를 제공할 것입니다.

다른 답변이 언급한 것처럼, 보통 무료 블록 목록이 나오겠지만, 무료로 전화하지 않았다면 하나만 있을 것이므로 두 경우 모두 O(1)이어야 합니다.

이것은 두 경우 모두 힙에 할당된 메모리가 충분히 크다는 것을 가정합니다.#1의 경우, 각 할당에는 메타 데이터를 저장하기 위한 메모리 오버헤드가 수반되므로, 결과적으로 sbrk()를 호출하거나 #1의 경우 힙을 증가시키기 위해 동등한 메모리를 호출해야 하므로, 추가 오버헤드가 발생할 수 있습니다.

새 할당에 대한 메모리 정렬이 동일하지 않기 때문에 캐시 및 기타 2차 효과로 인해 다를 수 있습니다.

일부 메모리 블록을 사용할 수 있었다면 조각화가 덜 되어 검색할 수 있는 사용 가능한 블록 목록이 적어 #2가 더 빨라질 가능성이 높습니다.

모든 메모리 블록을 자유롭게 사용했다면 블록을 다시 단일 메모리 영역으로 통합할 수 있기 때문에 완전히 동일한 상태로 끝날 것입니다.

Malloc은 할당할 블록을 찾기 위해 링크된 무료 블록 목록을 살펴봐야 합니다.시간이 걸립니다.따라서 #1은 보통 더 느립니다.

  • malloc에 자주 전화할수록 더 많은 시간이 소요됩니다. 따라서 통화 횟수를 줄이면 속도가 향상됩니다(정확한 상황에 따라 중요한지 여부가 달라집니다).

  • 또한 작은 블록을 많이 할당하면 해당 블록을 해제할 때 큰 블록 몇 개만 할당하고 해제하는 경우보다 힙을 훨씬 더 많이 조각화할 수 있습니다.따라서 몇 개의 큰 블록보다는 여러 개의 작은 빈 블록이 힙에 쌓이게 될 가능성이 높으며 따라서 mallocs는 할당할 적합한 블록을 찾기 위해 빈 공간 목록을 더 검색해야 할 수도 있습니다.그러면 또 더 느려질 겁니다

물론 구현 세부 사항이지만, 일반적으로free()메모리를 사용 가능한 블록 목록에 삽입합니다.malloc()그러면 이 목록에서 올바른 크기 이상의 사용 가능한 블록이 있는지 확인합니다.일반적으로 실패한 경우에만 해당됩니다.malloc()커널에 더 많은 메모리를 요구합니다.

인접한 여러 블록을 하나의 더 큰 블록으로 통합하는 경우와 같은 다른 고려 사항도 있습니다.

그리고 또 다른 이유는malloc()값이 비쌉니다: 만약malloc()여러 스레드에서 호출되며, 이러한 전역 구조에 어떤 종류의 동기화가 있어야 합니다.(즉, 자물쇠)존재합니다malloc()여러 스레드에서 더 나은 최적화 방식으로 구현하지만 일반적으로 여러 스레드에서 서로 잠금을 다투고 진행을 차단하기 때문에 다중 thread 안전을 유지하면 비용이 증가합니다.

malloc()를 사용하여 대용량 메모리를 할당하고 직접 세분화하여 더 나은 작업을 수행할 수 있습니다.Malloc()는 일반적인 경우에 잘 작동하도록 최적화되었으며 스레드를 사용하는지 여부 또는 프로그램의 할당 크기가 얼마인지에 대한 가정은 하지 않습니다.

자신의 하위 할당기를 구현하는 것이 좋은 아이디어인지 여부는 부차적인 질문입니다.명시적인 메모리 관리가 이미 충분히 어려운 경우는 거의 없습니다.디버그할 수 있는 좋은 방법 없이 프로그램을 엉망으로 만들고 손상시킬 수 있는 코드 계층이 필요한 경우는 거의 없습니다.디버그 할당기를 작성하는 경우가 아니라면요.

답은 그것이 달라지는데, 잠재적인 느림의 대부분은 오히려 malloc()와 free() 조합에서 오고 보통 #1과 #2는 비슷한 속도가 될 것이라는 것입니다.

모든 malloc() 구현에는 인덱싱 메커니즘이 있지만 인덱스에 새 블록을 추가하는 속도는 인덱스에 이미 있는 블록의 수에 따라 달라지지 않습니다.

malloc의 느림의 대부분은 두가지 원천에서 비롯됩니다.

  • 이전에 해제된 블록(블록) 중 적절한 사용 가능한 블록 검색
  • 잠금과 관련된 다중 processor 문제

나만의 거의 표준을 준수하는 malloc() 교체 도구 malloc() & free()를 35%에서 3-4%까지 작성하는 것은 이 두 가지 요소를 심각하게 최적화했습니다.다른 고성능 malloc을 사용하는 것과 비슷한 속도였을 것입니다. 하지만 우리 제품을 사용하는 것은 비밀스러운 장치에 더 휴대하기 쉬웠고 물론 어떤 곳에서는 무료로 줄을 설 수 있습니다.

"많은"과 "소수" 사이의 상대적인 차이를 정의하지는 않지만, 대부분의 말록은 두 시나리오에서 거의 동일하게 작동할 것이라고 생각합니다.이 질문은 malloc에 대한 각 호출이 시스템 호출 및 페이지 테이블 업데이트만큼 많은 오버헤드를 가지고 있음을 의미합니다.뇌사가 아닌 환경에서 malloc(14)와 같은 malloc 호출을 수행하면 malloc은 실제로 요청하는 것보다 더 많은 메모리를 할당하게 되며, 종종 시스템 MMU 페이지 크기의 배수가 됩니다.14바이트를 받으면 malloc이 새로 할당된 영역을 추적하여 나중에 호출하면 OS에서 더 많은 메모리를 요청해야 할 때까지 이미 할당된 메모리의 한 덩어리를 반환할 수 있습니다.

즉 malloc(14)를 100번이나 malloc(1400)를 한번 정도 부르면 오버헤드가 거의 같아집니다.더 큰 용량의 메모리 청크는 제가 직접 관리해야 합니다.

한 블록의 메모리를 할당하는 것이 여러 블록을 할당하는 것보다 빠릅니다.시스템 호출의 오버헤드가 있으며 사용 가능한 블록을 검색합니다.프로그래밍에서 작업 수를 줄이면 일반적으로 실행 시간이 빨라집니다.

메모리 할당자는 올바른 크기의 메모리 블록을 찾기 위해 검색해야 할 수도 있습니다.이로 인해 실행 시간의 오버헤드가 가중됩니다.

그러나 작은 메모리 블록을 할당할 때 큰 블록을 할당할 때보다 성공 가능성이 더 높을 수 있습니다.프로그램에서 하나의 작은 블록을 할당하고 해제합니까, 아니면 작은 블록을 할당(및 보존)해야 합니까?메모리가 단편화되면 사용할 수 있는 큰 청크가 적어지므로 메모리 할당자는 할당에 필요할 만큼 큰 블록을 형성하기 위해 모든 블록을 병합해야 할 수도 있습니다.

프로그램이 많은 작은 메모리 블록을 할당하고 파괴하는 경우 정적 배열을 할당하여 메모리에 사용하는 것을 고려해 볼 수 있습니다.

언급URL : https://stackoverflow.com/questions/2079151/minimizing-the-amount-of-malloc-calls-improves-performance