System.gc ()를 호출하는 것이 왜 나쁜 습관입니까?
Java로 객체 를 강제 사용하지 않는 방법 (1.5GB HashMap을 지우는 방법)에 대한 질문에 대답 한 후 수동으로 호출하는 것은 나쁜 습관이라고 들었지만 주석은 완전히 설득력이 없었습니다. 또한, 아무도 내 대답을 공감하거나 감히 내려 놓는 것처럼 보이지 않았습니다.System.gc()
System.gc()
나는 거기에 나쁜 습관이라고 들었지만 가비지 컬렉터 실행은 더 이상 체계적으로 세상을 멈추지 않으며 JVM에서 힌트로만 효과적으로 사용할 수 있다고 들었습니다. 손실에.
JVM이 메모리를 회수해야 할 때 일반적으로 사용자보다 더 잘 알고 있음을 이해합니다. 또한 몇 킬로바이트의 데이터에 대한 걱정은 어리 석다는 것을 이해합니다. 또한 메가 바이트의 데이터조차도 몇 년 전의 데이터가 아니라는 것을 이해합니다. 그러나 여전히 1.5 기가 바이트? 그리고 메모리에 1.5GB의 데이터가 걸려 있다는 것을 알고 있습니다. 어둠 속에서 촬영하는 것과는 다릅니다. 가 System.gc()
체계적으로 불량이거나 괜찮이되는 몇 가지 포인트가있다?
따라서 문제는 실제로 두 배입니다.
- 전화하는 것은 왜 나쁜 일
System.gc()
입니까? 실제로 특정 구현에서 JVM에 대한 힌트일까요? 아니면 항상 전체 수집주기입니까? 세상을 멈추지 않고 작업을 수행 할 수있는 가비지 수집기 구현이 실제로 있습니까? 사람들이 내 답변 에 대한 의견을 제시 한 다양한 주장에 대해 약간의 설명을 부탁드립니다 . - 임계 값은 어디에 있습니까? 에 전화하는 것은 좋은 생각 이 아니
System.gc()
거나 허용되는 시간이 있습니까? 그렇다면 그 시간은 무엇입니까?
모든 사람이 항상 피해야 System.gc()
하는 이유는 코드가 근본적으로 손상 되었다는 꽤 좋은 지표 이기 때문입니다 . 정확성에 의존하는 코드는 확실히 손상되었습니다. 성능에 의존하는 모든 것이 손상되었을 가능성이 큽니다.
어떤 종류의 가비지 수집기가 실행되고 있는지 알 수 없습니다. 확실히 당신이 주장하는 것처럼 "세계를 막지" 않는 것이 있지만, 일부 JVM은 그렇게 똑똑하지 않거나 여러 가지 이유로 (아마도 전화 중입니까?) 그렇게하지 않습니다. 당신은 그것이 무엇을할지 모른다.
또한 아무것도하지 않을 수도 있습니다. JVM은 요청을 완전히 무시할 수 있습니다.
"무엇을할지 모르겠다", "도움이 될지 모른다", "어쨌든 전화 할 필요가 없다"의 조합은 사람들이 일반적으로 당신은 그것을 호출해서는 안됩니다. "이것을 사용해야하는지 물어봐야한다면 안된다"고 생각합니다.
다른 스레드의 몇 가지 문제를 해결하도록 편집 하십시오.
링크 된 스레드를 읽은 후에 몇 가지 더 지적하고 싶습니다. 먼저 누군가 호출 gc()
하면 시스템에 메모리를 반환 할 수 있다고 제안했습니다 . Java 힙 자체는 Java 할당과 독립적으로 커집니다.
마찬가지로 JVM은 메모리 (수십 메가 바이트)를 보유하고 필요에 따라 힙을 증가시킵니다. Java 객체를 해제하더라도 시스템에 해당 메모리를 반환 할 필요는 없습니다. 향후 Java 할당에 사용하기 위해 할당 된 메모리를 보유 할 수 있습니다.
System.gc()
아무것도 할 수 없음을 나타내려면 다음을보십시오.
http://bugs.sun.com/view_bug.do?bug_id=6668279
특히 -XX : DisableExplicitGC VM 옵션이 있습니다.
호출 system.gc()
은 아무것도 할 수 없으며 가비지 콜렉터를 "실행해야하는"코드가 손상 되었다고 이미 설명했습니다 .
그러나 전화하는 것이 좋지 않은 실용적인 이유 System.gc()
는 비효율적이라는 것입니다. 그리고 최악의 경우, 그것은 매우 비효율적입니다 ! 설명하겠습니다.
일반적인 GC 알고리즘은 힙에있는 모든 비가 비지 개체를 통과하고 방문하지 않은 개체는 가비지 여야 함을 유추하여 가비지를 식별합니다. 이를 통해 가비지 콜렉션의 전체 작업을 실제 데이터 양에 비례하는 한 부분과 가비지 양에 비례하는 다른 부분으로 구성 할 수 있습니다. 즉 work = (live * W1 + garbage * W2)
.
이제 단일 스레드 애플리케이션에서 다음을 수행한다고 가정하십시오.
System.gc(); System.gc();
첫 번째 부름은 (우리가 예측 한) (live * W1 + garbage * W2)
일을하고 미지의 쓰레기를 제거 할 것입니다.
두 번째 부름은 (live* W1 + 0 * W2)
효과가 있으며 아무것도 되찾지 못할 것 입니다. 다시 말해 우리는 (live * W1)
일을 해왔고 전혀 아무것도 달성하지 못했습니다 .
가비지 단위를 수집하는 데 필요한 작업량으로 수집기의 효율성을 모델링 할 수 있습니다. 즉 efficiency = (live * W1 + garbage * W2) / garbage
. 따라서 GC를 최대한 효율적으로 만들려면 GC를 실행할 때 의 가치 를 극대화 해야합니다 garbage
. 즉, 힙이 가득 찰 때까지 기다리십시오. 또한 힙을 최대한 크게 만드십시오. 그러나 이는 별도의 주제입니다.
응용 프로그램이 (호출을 통해 System.gc()
) 방해하지 않으면 GC는 힙이 가득 찰 때까지 대기하여 가비지 1 을 효율적으로 수집 합니다. 그러나 응용 프로그램이 GC를 강제로 실행하면 힙이 가득 차지 않을 가능성이 있으며 결과적으로 가비지가 비효율적으로 수집됩니다. 그리고 응용 프로그램이 GC를 더 자주 강제할수록 GC가 더 비효율적으로됩니다.
참고 : 위의 설명은 일반적인 최신 GC가 힙을 "공간"으로 분할하고 GC가 힙을 동적으로 확장 할 수 있으며 응용 프로그램의 비가 비지 객체 작업 집합이 다양 할 수 있다는 사실을 강조합니다. 그럼에도 불구하고 동일한 기본 원칙이 모든 실제 가비지 수집기 2에 적용됩니다 . GC를 강제로 실행하는 것은 비효율적입니다.
1- "처리량"수집기가 작동하는 방식입니다. CMS 및 G1과 같은 동시 수집기는 서로 다른 기준을 사용하여 가비지 수집기를 시작할시기를 결정합니다.
2-참조 카운트를 독점적으로 사용하는 메모리 관리자도 제외하고 있지만 현재 Java 구현에서는 그 방법을 사용하지 않습니다 ...
많은 사람들이 당신에게 이것을하지 말라고 말하고있는 것 같습니다. 동의하지 않습니다. 레벨로드와 같은 큰로드 프로세스 후에 다음을 믿는 경우 :
- 도달 할 수없고 gc'ed되지 않은 많은 오브젝트가 있습니다. 과
- 이 시점에서 사용자가 약간의 둔화를 견딜 수 있다고 생각합니다.
System.gc ()를 호출해도 아무런 해가 없습니다. 나는 그것을 c / c ++ inline
키워드 처럼 본다 . 그것은 개발자에게 시간 / 성능이 평소만큼 중요하지 않으며 일부는 메모리를 회수하는 데 사용될 수 있다고 결정한 gc에 대한 힌트 일뿐입니다.
아무것도하지 않는 것에 대한 조언은 맞습니다. 작동에 의존하지 말고 지금은 수집하기에 적합한 시간이라는 힌트를주는 것이 좋습니다. 사용자가 프로그램과 적극적으로 상호 작용할 때 (게임 수준과 같이) 코드에서 중요하지 않은 (로드 화면) 시점에서 시간을 낭비하고 싶습니다.
한 번은 수집 을 강요 할 때가 있습니다. 특정 객체 누수 (기본 코드 또는 대규모의 복잡한 콜백 상호 작용)를 찾으려고 할 때 Matlab에서 볼 수있는 UI 구성 요소 는 절대 사용해서는 안됩니다 . 생산 코드에서.
사람들은 왜 사용하지 말아야 하는지를 잘 설명해 왔으므로 몇 가지 상황을 설명해야합니다.
(다음 주석은 CMS 콜렉터로 Linux에서 실행되는 Hotspot에 적용 System.gc()
되며 실제로는 항상 전체 가비지 콜렉션을 호출 한다고 확신 합니다.)
응용 프로그램을 처음 시작한 후에는 메모리 사용 상태가 끔찍할 수 있습니다. tenured 세대의 절반은 쓰레기로 가득 차있을 수 있습니다. 즉, 첫 CMS에 훨씬 가깝습니다. 중요한 응용 프로그램에서는 System.gc ()를 호출하여 힙을 라이브 데이터의 시작 상태로 "재설정"하는 것은 좋지 않습니다.
# 1과 동일한 행을 따라 힙 사용량을 면밀히 모니터링하는 경우 기준 메모리 사용량을 정확하게 읽습니다. 응용 프로그램의 가동 시간 중 처음 2 분이 모두 초기화 인 경우 전체 gc를 미리 설정하지 않으면 데이터가 엉망이됩니다.
tenured generation이 실행되는 동안 아무것도 홍보하지 않도록 설계된 응용 프로그램이있을 수 있습니다. 그러나 아마도 거대 세대가 아닌 세대로 자동으로 이동하려면 거대하지 않은 데이터를 미리 초기화해야 할 수도 있습니다. 모든 것이 설정된 후 System.gc ()를 호출하지 않으면 데이터가 승격 될 때까지 새로운 세대에 데이터가 저장 될 수 있습니다. 갑작스럽게 슈퍼 듀퍼 낮은 지연 시간, 낮은 GC 애플리케이션은 정상적인 작업 중에 이러한 객체를 승격시키는 데 대한 엄청난 지연 시간 (상대적으로 말하면) 지연 페널티에 부딪칩니다.
메모리 누수가 있는지 확인하기 위해 프로덕션 응용 프로그램에서 System.gc 호출을 사용하는 것이 유용한 경우가 있습니다. X 시점의 라이브 데이터 세트가 Y 시점의 라이브 데이터 세트에 대해 특정 비율로 존재해야한다는 것을 알고 있다면 System.gc ()에 X 시간과 Y 시간을 호출하고 메모리 사용량을 비교하는 것이 유용 할 수 있습니다 .
GC 효율성은 여러 가지 휴리스틱에 의존합니다. 예를 들어 일반적인 휴리스틱은 개체에 대한 쓰기 액세스가 일반적으로 오래 전에 생성되지 않은 개체에서 발생한다는 것입니다. 또 다른 하나는 많은 객체가 수명이 매우 짧다는 것입니다 (일부 객체는 오랫동안 사용되지만 생성 후 몇 마이크로 초 후에 폐기 됨).
전화 System.gc()
는 GC를 차는 것과 같습니다. "모든 신중하게 조정 된 매개 변수, 스마트 조직, 개체를 할당하고 관리하는 데 모든 노력을 기울여서 원활하게 진행할 수 있습니다. 그것은 수 있습니다 성능을 개선하지만, 그것은 단지 대부분의 시간을 저하 성능을.
System.gc()
안정적 으로 사용하려면 (*) GC가 세부적으로 어떻게 작동하는지 알아야합니다. 다른 벤더의 JVM 또는 동일한 벤더의 다음 버전 또는 동일한 JVM이지만 약간 다른 명령 행 옵션을 사용하는 경우 이러한 세부 사항은 상당히 변경되는 경향이 있습니다. 따라서 모든 매개 변수를 제어하는 특정 문제를 해결하지 않는 한 좋은 아이디어는 아닙니다. 따라서 "나쁜 습관"이라는 개념은 금지되어 있지 않으며 방법은 존재하지만 거의 보상을하지 않습니다.
(*) 여기서 효율성에 대해 이야기하고 있습니다. 올바른 Java 프로그램을 중단System.gc()
하지 않습니다 . JVM이 다른 방법으로는 얻을 수 없었던 추가 메모리를 활용하지는 않습니다.를 던지기 전에 JVM은 최후의 수단으로도 작업을 수행합니다 .OutOfMemoryError
System.gc()
때때로 ( 종종 그렇지는 않습니다! ) 런타임, 현재 및 미래의 메모리 사용량에 대해 더 많이 알고 있습니다. 이것은 자주 발생하지 않으며 일반 페이지가 제공되는 동안 웹 응용 프로그램에서 절대 주장하지 않습니다.
몇 년 전 저는 보고서 생성기에서 작업했습니다.
- 단일 스레드가 있었다
- 대기열에서 "보고서 요청"을 읽습니다.
- 데이터베이스에서 보고서에 필요한 데이터를로드했습니다.
- 보고서를 생성하여 이메일로 발송했습니다.
- 미해결 요청이 없을 때 잠을 영원히 반복했습니다.
- 보고서간에 데이터를 재사용하지 않았으며 현금화도하지 않았습니다.
먼저 실시간이 아니고 사용자가 보고서를 기다릴 것으로 예상했기 때문에 GC 실행은 문제가되지 않았지만 요청보다 빠른 속도로 보고서를 작성해야했습니다.
위의 프로세스 개요를 보면 분명히 알 수 있습니다.
- 다음 요청이 아직 처리되지 않았기 때문에 보고서가 이메일로 전송 된 직후에 실제 개체가 거의 없다는 것을 알고 있습니다.
- 가비지 콜렉션주기를 실행하는 비용은 라이브 오브젝트 수에 따라 다르며 가비지 양은 GC 실행 비용에 거의 영향을 미치지 않습니다.
- 대기열이 비어 있으면 GC를 실행하는 것이 더 좋습니다.
따라서 요청 큐가 비어있을 때마다 GC 실행을 수행하는 동안 가치가 있습니다. 이것에 대한 단점은 없었습니다.
GC 실행에 적합한시기임을 알 수 있으므로 각 보고서를 이메일로 보낸 후에 GC 실행을 수행하는 것이 좋습니다. 그러나 컴퓨터에 충분한 램이 있으면 GC 실행을 지연시켜 더 나은 결과를 얻을 수 있습니다.
이 동작은 각 보고서마다 보고서 보호 속도 를 크게 향상 시킨 후 강제 GC를 활성화하는 일부 고객을 위해 설치 기반별로 구성되었습니다 . (이것은 서버의 메모리가 부족하고 많은 다른 프로세스를 실행하기 때문에 GC가 페이징을 줄 이도록 충분한 시간을 가졌다 고 생각합니다.)
작업 대기열이 비어있을 때마다 강제 GC 실행이 도움이되지 않는 설치를 감지하지 못했습니다.
그러나 위의 내용은 일반적인 경우가 아닙니다.
이것은 매우 귀찮은 질문이며, 언어의 유용성에도 불구하고 많은 사람들이 Java에 반대하는 데 기여한다고 생각합니다.
"System.gc"가 무엇이든 할 수 없다는 사실은 믿을 수 없을 정도로 어렵고 "공포, 불확실성, 의심"느낌을 언어에 쉽게 부를 수 있습니다.
대부분의 경우 중요한 이벤트가 발생하기 전에 의도적으로 발생하는 메모리 스파이크를 처리하는 것이 좋습니다. 이로 인해 사용자는 프로그램이 잘못 설계되었거나 응답하지 않는다고 생각하게됩니다.
가비지 수집을 제어 할 수있는 능력은 매우 훌륭한 교육 도구이며, 가비지 수집이 작동하는 방식과 프로그램이 기본 동작 및 제어 된 동작을 악용하는 방법을 사람들의 이해도를 향상시킵니다.
이 스레드의 인수를 검토하겠습니다.
- 비효율적입니다.
종종 프로그램이 아무 것도하지 않을 수 있으며 프로그램 방식으로 인해 아무것도하지 않는 것을 알고 있습니다. 예를 들어, 큰 대기 메시지 상자를 사용하여 일종의 오래 기다릴 수 있으며 마지막에는 쓰레기를 수집하는 호출을 추가하여 실행 시간이 실제로는 오래 기다리지 만 더 중요한 작업 중에 gc가 작동하지 않도록합니다.
- 항상 나쁜 습관이며 깨진 코드를 나타냅니다.
동의하지 않습니다. 가비지 수집기가 무엇인지는 중요하지 않습니다. 그것의 임무는 쓰레기를 추적하고 청소하는 것입니다.
사용량이 덜 중요한 시간에 gc를 호출하면 수명이 특정 코드에 의존하지만 가비지를 수집하기로 결정할 때 실행 가능성을 줄입니다.
물론, 원하는 방식으로 작동하지 않을 수도 있지만 전화를 걸 때 아무 일도 일어나지 않으며 사용자는 속도 저하 / 다운 타임을 용인 할 수 있습니다. System.gc가 작동하면 훌륭합니다! 그렇지 않은 경우 최소한 시도했습니다. 가비지 수집기가 수동으로 호출 할 경우 가비지 수집기가 동작하는 방식에 예상치 못한 결과를 초래하는 고유 한 부작용이 없으면 단순히 단점이 없으며, 이는 자체적으로 불신을 야기합니다.
- 일반적인 사용 사례는 아닙니다.
안정적으로 달성 할 수없는 유스 케이스이지만 시스템이 그러한 방식으로 설계된 경우 일 수 있습니다. 교통 신호등을 만들고 교통 신호등의 일부 / 모든 버튼이 아무것도하지 않도록하는 것과 같습니다. 버튼이 시작되는 이유에 대한 의문을 제기하고, 자바 스크립트에는 가비지 수집 기능이 없으므로 그것을 면밀히 조사하지 마십시오.
- 사양에 따르면 System.gc ()는 GC를 실행해야한다는 힌트이며 VM은이를 무시할 수 있습니다.
"힌트"란 무엇입니까? "무시"란 무엇입니까? 컴퓨터는 단순히 힌트를 얻거나 무언가를 무시할 수 없으며, 시스템의 의도에 따라 동적 일 수있는 엄격한 행동 경로가 있습니다. 적절한 답변은 가비지 수집기가 실제로 구현 수준에서 수행하는 작업을 포함하며, 이는 요청시 수집을 수행하지 못하게합니다. 이 기능은 단순히 nop입니까? 어떤 조건이 충족되어야합니까? 이 조건들은 무엇입니까?
Java GC는 종종 당신이 믿지 않는 괴물처럼 보입니다. 언제오고 갈 것인지, 그것이 무엇을할지, 어떻게할지 모릅니다. 가비지 콜렉션이 명령별로 작동하는 방식에 대해 더 잘 알고있는 일부 전문가를 상상할 수 있지만 대다수는 단순히 "그냥 작동"하기를 희망하며 불투명 한 알고리즘을 신뢰하여 작업을 수행하는 것은 실망 스럽습니다.
무언가에 대해 읽거나 무언가를 배우는 것과 실제로 그것을 구현하는 것, 시스템 간의 차이점을 보는 것, 그리고 소스 코드를 보지 않고도 그것을 이용할 수있는 것에는 큰 차이가 있습니다. 이것은 자신감과 숙달 / 이해 / 통제 감을 만듭니다.
요약하자면, "이 기능은 아무 것도하지 않을 수 있으며, 어떤 일을 할 때와하지 않을 때, 왜하지 않을 것인지, 왜하지 않을 것인지에 대한 자세한 내용은 다루지 않겠습니다." "그 뒤에 의도가 합리적 일지라도 그것을 시도하는 것은 단순히 철학에 위배된다는 것을 암시한다."
Java GC가 작동하는 방식대로 작동하는 것이 좋을 수도 있고 그렇지 않을 수도 있지만 이해하기 위해서는 GC가 신뢰할 수있는 작업에 대한 포괄적 인 개요를 얻기 위해 어느 방향으로 나아가 야 하는지를 실제로 이해하기가 어렵습니다. 언어의 목적은 행동을 철학적으로 통제 할 수 있기 때문에 (언어가 특정 시스템 / 언어의 행동으로 인해 존재하는 위기에 빠지기 쉽다.) 용인 할 수 있고 (그렇지 않으면 언어를 사용하지 않을 것입니다.) 제어 할 수없는 알려진 이유없이 제어 할 수없는 것들은 본질적으로 해 롭습니다.
어색한 코드를 작성했을 수도 있지만 일식 및 넷빈즈 IDE에서 휴지통 아이콘을 클릭하는 것이 '좋은 습관'임을 깨달았습니다.
첫째, 사양과 현실에는 차이가 있습니다. 사양에 따르면 System.gc ()는 GC를 실행해야한다는 힌트이며 VM은이를 무시할 수 있습니다. 실제로 VM은 절대 System.gc () 호출을 무시 하지 않습니다 .
GC를 호출하면 호출에 사소한 오버 헤드가 제공되며 임의의 특정 시점 에서이 작업을 수행하면 노력에 대한 보상이 없을 것입니다. 반면에 자연스럽게 트리거되는 컬렉션은 통화 비용을 회수 할 가능성이 높습니다. System.gc ()를 호출 할 수있는 것보다 GC를 실행해야한다는 정보가 있으면 이점을 볼 수 있습니다. 그러나 System.gc ()를 호출 해야하는지 여부와 시간을 이해하기에 충분한 정보를 얻지 못할 가능성이 있기 때문에 몇 가지 경우에만 발생하는 것은 내 경험입니다.
IDE에있는 쓰레기통을 치면 여기에 나열된 예가 있습니다. 회의에 참석하지 않으면 회의에 참석하지 마십시오. 오버 헤드는 영향을 미치지 않으며 다시 돌아올 때 힙이 정리 될 수 있습니다. 생산 시스템에서이 작업을 수행하고 수집을 자주 요청하면 분쇄 작업이 중단됩니다! RMI의 전화와 같은 간혹 호출해도 성능이 저하 될 수 있습니다.
예. System.gc ()를 호출한다고해서 실행이 보장되는 것은 아니며 JVM에 대한 요청이므로 무시 될 수 있습니다. 문서에서 :
gc 메소드를 호출하면 Java Virtual Machine이 사용하지 않는 객체를 재활용하기 위해 노력을 소비 함을 제안합니다.
자동 메모리 관리는 일반적으로 gc를 할 때보 다 더 잘 알고 있기 때문에 호출하는 것은 거의 항상 나쁜 생각입니다. 사용 가능한 메모리의 내부 풀이 부족하거나 OS가 일부 메모리를 전달하도록 요청하는 경우 그렇게합니다.
당신이 경우에 System.gc ()를 호출하는 것이 허용 될 수 알고 그것을하는 데 도움이. 즉, 배포 플랫폼 에서 두 시나리오의 동작을 철저히 테스트하고 측정했으며 도움이 될 수 있습니다. gc는 쉽게 예측할 수 없다는 점을 명심하십시오-그것은 한 달리기에 도움이되고 다른 달리기에 상처를 줄 수 있습니다.
필자의 경험에 따르면 System.gc ()를 사용하는 것은 플랫폼 별 최적화 형식입니다 (여기서 "플랫폼"은 하드웨어 아키텍처, OS, JVM 버전 및 사용 가능한 RAM과 같은 더 많은 런타임 매개 변수의 조합입니다). 특정 플랫폼에서 대략 예측할 수 있지만 플랫폼마다 상당히 다를 수 있습니다.
예 . System.gc ()가 성능을 향상시키는 상황 이 있습니다 . 예를 들어 앱의 일부 부분에서는 지연이 허용되지만 다른 부분에서는 지연이 허용되지 않는 경우가 있습니다 (위에서 인용 한 게임 예제, 레벨이 아닌 레벨의 시작 부분에서 GC가 발생하도록하려는 경우).
그러나 그것이 도움이되는지 아프게 할 것인지 (또는 아무것도하지 않을 것인지)는 플랫폼에 따라 크게 좌우됩니다 (위에 정의 된대로).
따라서 마지막 리조트 플랫폼 별 최적화로 유효하다고 생각합니다 (즉, 다른 성능 최적화가 충분하지 않은 경우). 그러나 특정 벤치 마크없이 도움이 될 수 있다고 생각하기 때문에 전화해서는 안됩니다.
new 연산자를 사용하여 객체가 동적으로 할당되므로
이러한 객체가 어떻게 소멸되고
나중에 재 할당하기 위해 메모리가 해제 되는지 궁금 할 것 입니다.C ++와 같은 일부 언어에서는 동적으로 할당 된 객체를 delete 연산자를 사용하여 수동으로 해제해야합니다.
- 자바는 다른 접근법을 취한다. 자동으로 할당 해제를 처리합니다.
- 이를 수행하는 기술을 가비지 수집이라고합니다. 객체에 대한 참조가 존재하지 않으면 해당 객체는 더 이상 필요하지 않은 것으로 간주되며 객체가 차지하는 메모리를 회수 할 수 있습니다. C ++ 에서처럼 객체를 명시 적으로 제거 할 필요가 없습니다.
- 가비지 콜렉션은 프로그램 실행 중 산발적으로 만 발생합니다.
- 더 이상 사용되지 않는 하나 이상의 객체가 존재하기 때문에 발생하지 않습니다.
- 또한 다른 Java 런타임 구현은 가비지 콜렉션에 대한 다양한 접근 방식을 취하지 만 대부분의 경우 프로그램을 작성하는 동안 그것에 대해 생각할 필요가 없습니다.
내 2 센트 : 활동에 AnimationDrawables를로드하고 재생합니다. 이미지 뷰 배경을로드하고 재생 한 다음 한 번에 하나씩 null로 설정합니다. 액티비티를 종료 한 후 다시 빠르게 돌아 오면 메모리 부족 예외가 발생하기 전까지 3 ~ 4 회 정도 참여한 메모리가 너무 커집니다.
imageview background를 null로 설정 한 후 가비지 수집기를 명시 적으로 호출하면 Eclipse logcat에서 메모리가 충분히 사용 가능한 상태로 유지되고 내 경우에는 gc가 실제로 실행되고 더 이상 앱 작동이 중지되지 않습니다.
시스템이 gc의 실행을 연기하기로 결정할 수도 있지만, gc의 작동 방식을 어느 정도 알고 있다면 가능한 한 빨리 호출 될 것입니다. 응용 프로그램은 시스템에 더 많은 것을 요구하려고합니다. 나는 그것이 C ++ std 라이브러리 컨테이너처럼 작동한다고 생각합니다. 시작 메모리가 있고 충분하지 않을 때마다 두 배가됩니다.
호출 할 필요가 있다면 코드가 깨지거나 잘못 되었기 때문에 나에게 대답하는 비합리적인 독단적 방법입니다. 특히 C ++과 같은 전체 수동 메모리 관리를 사용하여 언어로 프로그래밍 할 수 있고 리소스 제한에 직면 해야하는 경우 대신 자바와 같은 언어를 사용하는 모바일 장치를 사용하면 수동으로 메모리를 확보 할 수 없으므로 참조를 계산하지 않고 추적 gc가있는 곳에서 gc를 명시 적으로 호출 해야하는 많은 상황을 신속하게 생각할 수 있습니다. 깨끗하고 잘되었습니다.
참고 URL : https://stackoverflow.com/questions/2414105/why-is-it-bad-practice-to-call-system-gc
'Programing' 카테고리의 다른 글
핵심 데이터 대 SQLite 3 (0) | 2020.03.09 |
---|---|
명령 행에서 JUnit 테스트 케이스를 실행하는 방법 (0) | 2020.03.09 |
루비 해시 객체를 JSON으로 변환하는 방법? (0) | 2020.03.09 |
스택의 목적은 무엇입니까? (0) | 2020.03.09 |
@RequestParam 및 @PathVariable (0) | 2020.03.09 |