2012-05-15 6 views
4

AsyncTask # doInBackground 내에서 Android 컨텍스트를 사용할 때 스레드 안전합니까? 컨텍스트는 생성자를 통해 또는 주변 Activity의 getApplicationContext()를 통해 제공됩니다. 이 간단한 질문은 stackoverflow에서 많은 질문을 받았지만 어디에서 명확한 대답을 찾지 못했습니까?안드로이드 컨텍스트 스레드가 안전합니까?

예. doInBackground()에서 DAO 클래스를 인스턴스화하기 위해 컨텍스트를 사용합니다.

@Override 
protected Void doInBackground(Void... params) { 

    ExampleDao dao = new ExampleDao(context); 
    ... 

} 

나는이 방법으로 그 일을 몇 가지 예를 보았다, 그러나 나는 상황이 지금 주요 트레드 (UI 스레드) 및 작업자 스레드에 의해 액세스 할 수 있기 때문에이, 스레드 안전하다는 이미지 수 없습니다.

+0

좀 더 화를 잘 낼 수 있습니까? 정확히 무엇을하고 있습니까? –

+0

왜 스레드 안전하지 않아야합니까? 작업자 스레드는 컨텍스트를 사용하여 파일 시스템에 액세스하고 UI 스레드는 모든 UI 관련 항목에 대한 컨텍스트를 사용합니다. 동일한 리소스 등에 액세스하는 혼합 호출에 문제가 없어야합니다. – Janusz

답변

5

무언가를 변경하지 않고 컨텍스트를 통해서만 리소스를 검색하면 다른 스레드의 컨텍스트에 항상 액세스 할 수 있습니다. 스레드 안전성에 문제가 보이지 않습니다.

문제는 스레드가 실행되는 동안 컨텍스트가 메모리에 남아 활성 상태라는 것입니다. 항상 유효한 컨텍스트를 사용하는 데 의존 할 수 있기 때문에 이는 좋은 일입니다. 나쁜 점은 Activity를 컨텍스트로 전달하면이 활동의 ​​모든 뷰와 멤버 변수도 메모리에 남아있게되므로 Waqas와 같이 많은 메모리에 대해 매우 늦은 가비지 수집이 발생할 수 있다는 것입니다.

다른 스레드에서 수행하지 않는 작업에 대해서는 현재 표시된보기에 영향을주는 setTheme()과 같은 컨텍스트 하위 클래스의 메서드에 액세스하고 있습니다.

+0

좋은 소리가 나므로 전체 활동을 AsyncTask에 전달하는 대신 getApplicationContext()를 사용하는 것이 좋습니다. – dan

+0

예 응용 프로그램 컨텍스트를 전달하면 결코 해를 끼치 지 않으며 Java에서 찾기 어려운 이상한 메모리 문제로부터 사용자를 보호하지 않습니다. – Janusz

2

당신이 전망 아무것도 할 필요가없는 경우 후 항상 응용 프로그램의 컨텍스트 (안 활동의 컨텍스트)를 참조 getApplicationContext()를 사용하려고 및 스레딩 또는 방향 - 변경하면서 메모리 누수를 방지 할 수 있습니다. 그래서, 나는 그것이 AsyncTask에서 당신의 필요에 맞을 것 같아요.

+0

이것은 작업자 스레드의 UI 스레드에서 컨텍스트에 indepent 액세스 할 수 있음을 의미합니다. – dan

+0

예 ... 할 수 있습니다. – waqaslam

1

컨텍스트가 실제로 threadsafe가 아닙니다. 그러나 예를 들어 db에 쓰려면 응용 프로그램 컨텍스트의 인스턴스를 전달하는 것이 좋습니다.

+1

내 지식만으로도 "컨텍스트가 threadsafe가 아님"을 조금 더 설명 할 수 있습니까? 내 말은 왜 그렇지 않은거야? – waqaslam

+0

UI 스레드와 작업자 스레드의 예제에서 서로 다른 두 개의 스레드에서 컨텍스트에 액세스한다는 의미입니다. – dan

+1

쓰기 읽기 작업에는 동기화가 없다는 의미에서 스레드 안전성이 없습니다. 그러나 아무 것도 쓰지 않으므로 다른 스레드에서 사용할 수 있습니다. –

관련 문제