티스토리 뷰

오늘은 모바일 앱 개발 프로젝트를 진행하면서 겪었던 doInBackGround 진입 문제에 대해서 다뤄보고자 한다. 

내가 겪었던 문제는 AsyncTask를 사용하여 비동기식으로 동작을 실행 시킬때 백그라운드에서 돌아가는 부분인 doInBackGround() 함수가 진입이 되지 않는 다는 것이었다. 

 

문제의 원인을 몰라서 한참 헤맸는데, 원인은 두가지이다. 

 

 

|원인

1. 해당 비동기 클래스가 실행 될때 다른 비동기 클래스의 작업이 동시에 실행되는 경우 (일반적)

 

2. AsyncTask 를 extends한 비동기클래스  doInBackGround 내에서 또 다른 비동기 클래스를 호출하여 실행 시키는 경우.

 

 

 

 

|케이스 별 해결 방법

1. 원인 1의 경우

일반적으로 주로 쓰이는 해결 법이다.

아래는 문제가 있던 나의 코드 이다. 

public List<String> getCalendarDay(String dateMonth, Integer waterAc) {
    try{
        Log.d("DB", "getCalendarDay: hey");
        return new GetCalendarDay(pdDao, dateMonth, waterAc).excute().get();	//이게 문제
    } catch (InterruptedException | ExecutionException e) {
        Log.d("DB", "getCalendarDay: catch");
        e.printStackTrace();
        return null;
    }

 

일반적으로 doInBackGround를 실행시킬때 excute()를 많이 사용한다.

하지만 쓰레드가 여러개 돌아가면서 충돌 하는 것을 막기 위해서는, 아래와 같이 excute() 대신

excutionOnExecutor(AsyncTask.THREAD_POOL_EXCUTOR)을 사용 하면 된다.

 

public List<String> getCalendarDay(String dateMonth, Integer waterAc) {
    try{
        Log.d("DB", "getCalendarDay: hey");
        return new GetCalendarDay(pdDao, dateMonth, waterAc).executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR).get();
    } catch (InterruptedException | ExecutionException e) {
        Log.d("DB", "getCalendarDay: catch");
        e.printStackTrace();
        return null;
    }
}

 

이렇게 바꿔주면 대부분의 호출 문제는 해결 할 수 있다.

 

 

 

 

2. 원인 2의 경우

비 동기 클래스 내에서 다른 비동기 클래스를 호출하여 실행 시키는 경우에는 1번 해결법으로 해결이 되지 않는다.

그럴때에는 따로 내부에서 실행시켜야 하는 비동기 클래스를 다른 곳에서 실행 시키고 그 결과값을 가져오는 형태로 코드를 변형하면 된다. 

 

아래는 예시 코드이다. for 문 내부를 보면 historyViewModel.getCalendarDayList() 함수를 실행하는 것을 볼수 있다.

기존에 여기서 바로 비동기 클래스를 호출해서 에러가 났기 때문에 따로  함수를 만들어 historyViewModel.getCalendarDayList 에서 동작시키고, 결과 값만 받도록 수정하였다. 

 

    private class AddDecorate extends AsyncTask<Void, Void, Boolean> {

        @Override
        protected Boolean doInBackground(Void... voids) {
            ArrayList<CalendarDay> calendarDayList = new ArrayList<>();
            ArrayList<String> tempCalendarDayList = new ArrayList<>();
            calendarDayList.add(CalendarDay.today());

            for(int waterAc = 1; waterAc <6; waterAc++) {
            //에러발생
                tempCalendarDayList = historyViewModel.getCalendarDayList(CalendarDay.today().getMonth(), waterAc);
                Log.d("DB", "doInBackground: 리스트1  "+tempCalendarDayList);
                for(String day : tempCalendarDayList) {
                    String days[] = day.split("-");
                    Integer d = Integer.parseInt(days[2]);
                    Log.d("day", "doInBackground: "+CalendarDay.today()+"hello"+d);
                    calendarDayList.add(CalendarDay.from(CalendarDay.today().getYear(), CalendarDay.today().getMonth(), d)); //형식
                }
                cv_calendar.addDecorators(new EventDecorator(calendarDayList, getContext(), waterAc));
                calendarDayList.clear();
            }

            return null;
        }
    }

 

 

공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
«   2024/05   »
1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31
글 보관함