뷰 홀더가있는 Android Recyclerview 및 ListView


148

나는 최근 RecyclerView에 안드로이드 5.0과 함께 출시 된 안드로이드 를 발견했으며 ViewHolder 패턴이 통합 RecyclerView된 캡슐화 된 전통 인 것처럼 보이며 ListView매번 생성하는 대신보기의 재사용을 촉진합니다.

사용의 다른 장점은 무엇입니까 RecyclerView? 둘 다 성능면에서 동일한 효과가 있다면 왜 RecyclerView를 선호합니까?

편집하다

나는 사람들이 비슷한 질문을했고 그 답을 결정적이지 않아서 기록을 유지하기 위해 여기에 추가했습니다.

Recyclerview와 Listview

RecyclerView를 사용하여 ListView를 바꿔야합니까?

왜 RecyclerView에 onItemClickListener ()가 없습니까? 그리고 RecyclerView는 Listview와 어떻게 다른가요?


4
(가) 때문에 RecyclerView더 빠르고 더 나은 API와 다양한 정도입니다. 항목 추가 또는 제거 애니메이션과 같은 작업은 이미 수행 RecyclerView하지 않아도 이미 구현되어 있습니다. 그것에 대해 의문의 여지가 없습니다, 당신 ListView의 쓰레기통에 던져 , RecyclerView여기 쇼를 훔칠 수 있습니다 .
Xaver Kapeller

4
레이아웃 관리자를 RecyclerView와 연결할 수 있으므로 세로 스크롤 목록에만 국한되지 않습니다. 이것은 매우 강력한 추가 기능입니다.
Alan

@Alan- "수직 스크롤 목록에만 국한되지 않음"은 무슨 뜻입니까? Recycle View가 Gridview 및 ListView의 "자리 표시 자"역할을 할 수 있다고 말하고 있습니까?
Mushtaq Jameel

@ XaverKapeller-둘 사이의 차이점을 나열하고 의견이 아닌 질문에 대답 할 수 있다면 좋을 것입니다. 따라서 앞으로 나와 같은 사람에 대해 궁금해 할 수있는 다른 사람들을 도울 수 있습니까?
Mushtaq Jameel

@Alan-당신은 당신이 의미하는 것에 대해 약간의 세부 사항을 제공하고 의견보다는 질문에 대답 할 수 있습니까? 시간 내 주셔서 감사합니다
Mushtaq Jameel

답변:


289

Android Lollipop이 등장하면서 RecyclerView 가 공식적으로 나왔습니다 . RecyclerView는 훨씬 강력하고 유연하며 ListView보다 크게 향상되었습니다 . 이에 대한 자세한 통찰력을 제공 할 것입니다.

1) ViewHolder 패턴

ListView에서는 ViewHolder 패턴을 사용하는 것이 좋지만 절대로 강제하지는 않았습니다. RecyclerView의 경우 RecyclerView.ViewHolder 클래스를 사용해야합니다 . 이것은 ListView와 RecyclerView의 주요 차이점 중 하나입니다.

RecyclerView에서 일을 좀 더 복잡하게 만들지 만 ListView에서 직면 한 많은 문제가 효율적으로 해결됩니다.

2) LayoutManager

이것은 RecyclerView에 또 다른 큰 향상입니다. ListView에서 사용 가능한 유일한보기 유형은 세로 ListView입니다. 수평 ListView를 구현하는 공식적인 방법은 없습니다.

이제 RecyclerView를 사용하여

i) LinearLayoutManager- 세로 및 가로 목록을 모두 지원합니다.

ii) StaggeredLayoutManager-스 태거리스트처럼 Pinterest를 지원합니다.

iii) GridLayoutManager- 갤러리 앱에서 볼 수있는 그리드 표시를 지원합니다.

가장 좋은 점은 원하는대로이 모든 것을 동적으로 수행 할 수 있다는 것입니다.

3) 아이템 애니메이터

ListViews는 우수한 애니메이션을 지원하지 않지만 RecyclerView는 완전히 새로운 차원을 가져옵니다. RecyclerView.ItemAnimator 클래스를 사용하면 뷰 애니메이션이 훨씬 쉽고 직관적입니다.

4) 아이템 장식

ListView의 경우 테두리 또는 구분선 추가와 같은 항목을 동적으로 장식하는 것은 결코 쉬운 일이 아닙니다. 그러나 RecyclerView의 경우 RecyclerView.ItemDecorator 클래스는 개발자에게 강력한 제어 기능을 제공하지만 시간이 많이 걸리고 복잡합니다.

5) OnItemTouchListener

AdapterView.OnItemClickListener 인터페이스 덕분에 ListView에서 항목 클릭을 가로채는 것이 간단했습니다 . 그러나 RecyclerView는 RecyclerView.OnItemTouchListener ( 더 이상 지원되지 않음, AndroidX 참조)에 의해 개발자에게 훨씬 더 강력한 기능과 제어 기능을 제공하지만 개발자 에게는 약간 복잡합니다.

간단히 말해서, RecyclerView는 ListView보다 훨씬 더 사용자 정의가 가능하며 개발자에게 많은 제어 및 힘을 제공합니다.


34
좋은 대답입니다. 몇 가지 추가 장점 : RecyclerView는 보이는 항목 바로 앞과 뒤에서보기를 준비합니다. 백그라운드에서 비트 맵을 가져 오는 경우 유용합니다. 특히 RecyclerView.setHasFixedSize를 사용하면 성능이 크게 빨라집니다. 이전 ListView는 목록에서 항목의 크기를 미리 계산하거나 캐시 할 수있는 방법이 없다는 전제를 기반으로하며, 이는 스크롤 및 레이아웃을 수행 할 때 미친 합병증을 유발합니다. 익숙해지기까지 시간이 걸리지 만 일단 사용하면 다시는 돌아올 수 없습니다.
Robin Davies

@RobinDavies 탁월한 지적입니다. 알려 주셔서 감사합니다. 그러나 항목의 크기가 다른 경우에는 의미가 없습니다.
Aritra Roy

@AritraRoy Recyclerview는 롤리팝 만 지원 또는 API 14+ (android 4+)도 지원합니다. .... "롤리팝 이후 : 대부분의 장소에서
Animesh Mangla

2
안녕하세요, Aritra, ListView와 비교할 때 ListView가 ViewHolder 패턴을 사용하는 경우 어느 것이 더 효율적으로 작동합니까? ? 더 나은, FPS 또는 기타 이와 유사한 기준을 사용하는 경우 들으 RecylerView 것이다 ~
RxRead

@RxRead : Robin의 의견을 참조하십시오. 그는 성능의 관점에서 RecyclerView Vs ListView와 뷰 홀더 패턴을 차별화합니다.
Parag Kadam

10

사용의 또 다른 장점 RecycleView은 애니메이션이며 두 줄의 코드로 수행 할 수 있습니다

RecyclerView.ItemAnimator itemAnimator = new DefaultItemAnimator();
        recyclerView.setItemAnimator(itemAnimator);

그러나 위젯은 여전히 ​​원시적입니다. 예를 들어 headerfooter를 만들 수 없습니다 .


5
그런 의미에서 머리글과 바닥 글을 만들 수 없습니다. 어댑터의 다른보기 유형 일뿐입니다. 목록보기 HeaderViewListAdapter는 어댑터를 감싸고 백그라운드에서 헤더 지원을 추가합니다. RecyclerView당신 과 함께 당신이 제어 할 수 있습니다.
Eugen Pechanec

RecyclerView는 기본적으로 DefaultItemAnimator를 사용합니다. 그렇다면 왜이 코드를 사용 했습니까?
Athira Reddy 2018

9

약간 파고 들었고 빌 필립스 기사 에서이 보석을 발견 했습니다.RecycleView

RecyclerView는 ListView 이상을 수행 할 수 있지만 RecyclerView 클래스 자체는 ListView보다 책임이 적습니다. 기본적으로 RecyclerView는 다음을 수행하지 않습니다.

  • 화면에 항목 배치
  • 애니메이션 뷰
  • 스크롤 이외의 모든 터치 이벤트 처리

이 모든 것들이 ListView에 구워졌지만 RecyclerView는 공동 작업 클래스를 사용하여 대신 이러한 작업을 수행합니다.

생성 한 ViewHolders도 더 강력합니다. 그것들 RecyclerView.ViewHolder은 많은 메소드를 RecyclerView 사용 하는 서브 클래스 입니다. ViewHolders현재 바인딩 된 위치와 항목 ID (있는 경우)를 알고 있어야합니다. 그 과정에서 ViewHolder 기사단이되었습니다. 예전에는 전체 항목보기를 유지하기 위해 ListView의 작업이었고 ViewHolder작은 부분 만 유지했습니다.

이제 ViewHolder는 ViewHolder.itemView ViewHolder의 생성자에 지정된 필드의 모든 항목을 보유 합니다.


4

Bill Phillip의 기사 에서 더 많은 내용을 읽으십시오 (읽어보십시오!).하지만 다음을 지적하는 것이 중요하다고 생각했습니다.

ListView에는 클릭 이벤트를 처리하는 방법에 대한 모호성이있었습니다. 개별 뷰가 해당 이벤트를 처리해야합니까, 아니면 ListView가 OnItemClickListener를 통해 처리해야합니까? 그러나 RecyclerView에서 ViewHolder는 이러한 종류의 세부 정보를 처리하는 행 수준 컨트롤러 개체로 작동하기에 분명한 위치에 있습니다.

우리는 LayoutManager가 포지셔닝 뷰를 처리하고 ItemAnimator가 애니메이트를 처리하는 것을 앞에서 보았습니다. ViewHolder는 마지막 부분입니다. RecyclerView가 표시하는 특정 항목에서 발생하는 모든 이벤트를 처리합니다.


2

나는 ListView메모리 증가를 가진 글라이드 이미지 로더와 함께 사용했다 . 그런 다음를로 대체 ListView했습니다 RecyclerView. 코딩이 더 어려울뿐만 아니라 a보다 더 많은 메모리를 사용합니다 ListView. 적어도 내 프로젝트에서는.

다른 활동에서와 함께 복잡한 목록을 사용했습니다 EditText's. 그들 중 일부에서는 입력 방법이 다를 TextWatcher수 있으며 또한 적용될 수 있습니다. 를 사용한 경우 스크롤 ViewHolder하는 TextWatcher동안 어떻게 교체 할 수 있습니까? 그래서을 사용 ListView하지 않고 ViewHolder작동했습니다.


ViewHolder없이 ListView를 사용했는데 작동합니다. 끔찍한 아이디어 ... 스크롤하는 동안 TextWatcher를 어떻게 바꿀 수 있습니까? 교체 할 필요가 없습니다. TextWacher는 재사용 후 다른 컨테이너에 데이터를 저장해야합니다. 정말 간단합니다.
Selvin

@Selvin, 귀하의 의견에 감사드립니다. 이제 해당 프로젝트를 편집 할 수 없습니다. TextWatcher화면에 몇 개가있었습니다 . 아마 당신 말이 맞지만, 나는 그것을 확인할 수 없습니다.
CoolMind

1

위 / 아래로 스크롤하는 동안 셀을 재사용 합니다. listView 어댑터에서 View Holder를 구현하면 가능하지만 선택 사항이지만 RecycleView에서는 어댑터를 작성하는 기본 방법입니다.

컨테이너에서 목록을 분리합니다. 따라서 LayoutManager를 설정하여 런타임에 다른 컨테이너 (linearLayout, gridLayout)에 목록 항목을 쉽게 넣을 수 있습니다.

예:

mRecyclerView = (RecyclerView) findViewById(R.id.recycler_view);
mRecyclerView.setLayoutManager(new LinearLayoutManager(this));
//or
mRecyclerView.setLayoutManager(new GridLayoutManager(this, 2));
mRecyclerView.setLayoutManager(new GridLayoutManager(this, 3));
  • 공통 목록 동작에 애니메이션을 적용합니다.

  • 애니메이션이 분리되어에 위임되었습니다 ItemAnimator.

RecyclerView에 대한 자세한 내용이 있지만 이러한 점이 주요 사항이라고 생각합니다.

LayoutManager

i) LinearLayoutManager-세로 및 가로 목록을 모두 지원합니다.

ii) StaggeredLayoutManager-스 태거리스트처럼 Pinterest를 지원합니다.

iii) GridLayoutManager-갤러리 앱에서 볼 수있는 그리드 표시를 지원합니다.

가장 좋은 점은 원하는대로이 모든 것을 동적으로 수행 할 수 있다는 것입니다.


1

1. 뷰 홀더

ListView에서 뷰 홀더를 정의하는 것이 뷰에 대한 참조를 유지하기위한 제안 된 방법입니다. 그러나 그것은 강제가 아니었다. 그렇게하지 않아도 ListView는 오래된 데이터를 표시합니다. 뷰 홀더를 사용하지 않는 데 따른 또 다른 주요 단점은 매번 ID별로 뷰를 찾는 작업이 많이 발생할 수 있습니다. 결과적으로 지연된 ListView가 발생했습니다.

이 문제는 RecylerView에서 RecyclerView.ViewHolder 클래스를 사용하여 해결됩니다. 이것이 RecyclerView와 ListView의 주요 차이점 중 하나입니다. RecyclerView를 구현할 때이 클래스는 ViewHolder를 위치와 바인딩하기 위해 어댑터에서 사용하는 ViewHolder 객체를 정의하는 데 사용됩니다. 여기서 주목해야 할 또 다른 요점은 RecyclerView 용 어댑터를 구현하는 동안 ViewHolder를 제공하는 것이 필수적이라는 것입니다. 이를 통해 구현이 약간 복잡해 지지만 ListView에서 직면 한 문제를 해결합니다.

2. 레이아웃 관리자

ListView에 대해 말할 때 세로 ListView와 같은 한 가지 유형의 ListView 만 사용할 수 있습니다. 가로 스크롤로 ListView를 구현할 수 없습니다. 가로 스크롤을 구현하는 방법이 있지만 그 방식으로 작동하도록 설계되지 않았다고 생각합니다.

그러나 이제 Android RecyclerView와 ListView를 살펴볼 때 수평 컬렉션도 지원합니다. 실제로 여러 유형의 목록을 지원합니다. 여러 유형의 목록을 지원하기 위해 RecyclerView.LayoutManager 클래스를 사용합니다. 이것은 ListView에없는 새로운 것입니다. RecyclerView는 세 가지 유형의 사전 정의 된 레이아웃 관리자를 지원합니다.

LinearLayoutManager – RecyclerView의 경우 가장 일반적으로 사용되는 레이아웃 관리자입니다. 이를 통해 가로 및 세로 스크롤 목록을 모두 만들 수 있습니다. StaggeredGridLayoutManager –이 레이아웃 관리자를 통해 엇갈린 목록을 만들 수 있습니다. Pinterest 화면처럼. GridLayoutManager –이 레이아웃 관리자는 모든 사진 갤러리와 같이 격자를 표시하는 데 사용할 수 있습니다.

3. 아이템 애니메이터

목록의 애니메이션은 완전히 새로운 차원이며 무한한 가능성이 있습니다. ListView에는 항목을 애니메이션, 추가 또는 삭제할 수있는 특수한 조항이 없습니다. 나중에 안드로이드가 진화함에 따라 ListProperty의 애니메이션에 대한이 비디오 자습서에서 Google의 Chet Haase가 ViewPropertyAnimator를 제안했습니다.

반면 Android RecyclerView와 ListView를 비교하면 애니메이션 처리를위한 RecyclerView.ItemAnimator 클래스가 있습니다. 이 클래스를 통해 항목 추가, 삭제 및 이동 이벤트에 대한 사용자 정의 애니메이션을 정의 할 수 있습니다. 또한 사용자 정의가 필요하지 않은 경우 DefaultItemAnimator를 제공합니다.

4. 어댑터

ListView 어댑터는 구현이 간단했습니다. 그들은 모든 마술이 일어났던 주요 방법 인 getView를 가졌습니다. 뷰가 위치에 바인딩 된 위치 또한 어댑터에서 관찰자를 바로 설정할 수있는 흥미로운 메소드 registerDataSetObserver를 사용했습니다. 이 기능은 RecyclerView에도 있지만 RecyclerView.AdapterDataObserver 클래스가 사용됩니다. 그러나 ListView의 장점은 세 가지 기본 어댑터 구현을 지원한다는 것입니다.

ArrayAdapter CursorAdapter SimpleCursorAdapter RecyclerView 어댑터는 DB 커서 및 ArrayList에 대한 기본 지원을 제외하고 ListView 어댑터가 가진 모든 기능을 갖습니다. 현재 RecyclerView.Adapter에서는 어댑터에 데이터를 제공하기 위해 사용자 정의 구현을 작성해야합니다. BaseAdapter가 ListViews와 마찬가지로. RecyclerView 어댑터 구현에 대한 자세한 내용은 Android RecyclerView 예를 참조하십시오.

5. 데이터 변경 알림

ListView로 작업 할 때 데이터 세트가 변경되면 기본 어댑터의 notifyDataSetChanged 메소드를 호출하여 데이터를 새로 고쳐야합니다. notifyDataSetChanged 메소드를 자동으로 호출하려는 경우 setNotifyOnChange 메소드를 true로 설정하십시오. 그러나 두 경우 모두 목록에 나오는 결과는 매우 무겁습니다. 기본적으로 목록보기를 새로 고칩니다.

그러나 RecyclerView 어댑터와 달리 단일 항목 또는 항목 범위가 변경된 경우 그에 따라 변경 사항을 알리는 방법이 있습니다. 각각 notifyItemChanged 및 notifyItemRangeChanged이며 다음과 같습니다.

notifyItemInsterted notifyItemMoved notifyItemRangeInsterted notifyItemRangeRemoved 물론 전체 목록을 새로 고치는 원래 메소드가 있습니다. 즉 notifyDataSetChanged는 적응 된 전체 데이터 세트가 변경되었음을 알립니다.

6. 아이템 장식

ListView에 사용자 지정 구분선을 표시하기 위해 ListView XML에 이러한 매개 변수를 쉽게 추가 할 수 있습니다.

XHTML android : divider = "@ android : color / transparent"android : dividerHeight = "5dp"1 2 android : divider = "@ android : color / transparent"android : dividerHeight = "5dp"Android RecyclerView의 흥미로운 부분은 현재로서는 기본적으로 항목 사이에 구분선이 표시되지 않습니다. Google 직원은 의도적으로 맞춤 설정을 위해이 기능을 생략해야합니다. 그러나 이것은 개발자의 노력을 크게 증가시킵니다. 항목 사이에 구분선을 추가하려면 RecyclerView.ItemDecoration 클래스를 사용하여 사용자 지정 구현을 수행해야 할 수 있습니다.

또는 공식 샘플에서이 파일을 사용하여 해킹을 적용 할 수 있습니다 : DividerItemDecoration.java

7. OnItemTouchListener

클릭 감지를위한 간단한 구현, 예를 들어 AdapterView.OnItemClickListener 인터페이스를 사용하여 목록보기를 사용했습니다.

그러나 반면 RecyclerView.OnItemTouchListener 인터페이스는 Android RecyclerView에서 터치 이벤트를 감지하는 데 사용됩니다. 구현이 약간 복잡하지만 터치 이벤트를 가로 채기 위해 개발자에게 더 큰 제어 기능을 제공합니다. 공식 문서에 따르면 제스처 이벤트가 RecyclerView에 전달되기 전에 터치 이벤트를 가로 채기 때문에 제스처 조작에 유용 할 수 있습니다.


1

RecyclerView는 ListView 개선으로 작성되었으므로 ListView 컨트롤을 사용하여 첨부 목록을 만들 수 있지만 RecyclerView를 사용하는 것이 더 쉽습니다.

  1. 위 / 아래로 스크롤하는 동안 셀을 재사용 합니다. ListView 어댑터에서 View Holder를 구현하면 가능하지만 선택 사항이지만 RecycleView에서는 어댑터를 작성하는 기본 방법입니다.

  2. 컨테이너에서 목록을 분리 : LayoutManager를 설정하여 런타임에 다른 컨테이너 (linearLayout, gridLayout)에 목록 항목을 쉽게 넣을 수 있습니다.

mRecyclerView = (RecyclerView) findViewById (R.id.my_recycler_view); mRecyclerView.setLayoutManager (새로운 LinearLayoutManager (this)); mRecyclerView.setLayoutManager (새로운 GridLayoutManager (this, 2));

  1. 공통 목록 동작 애니메이션 : 애니메이션이 분리되어 ItemAnimator에 위임됩니다. RecyclerView에 대한 자세한 내용이 있지만 이러한 점이 주요 사항이라고 생각합니다.

결론적으로, RecyclerView는 우려의 위임 패턴을 따르는 "목록 데이터"를 처리하기위한보다 융통성있는 제어입니다.


0

RecycleView를 사용하는 경우 먼저 설정에 더 많은 efford가 필요합니다. 간단한 항목 onclick, 테두리, 터치 이벤트 및 기타 간단한 것을 설정하는 데 더 많은 시간을 주어야합니다. 그러나 최종 제품은 완벽 할 것입니다.

따라서 결정은 당신의 것입니다. 전화 번호부 로딩과 같은 간단한 응용 프로그램을 디자인하면 항목을 클릭하는 것만으로도 충분한 경우 목록보기를 구현할 수 있습니다. 그러나 무제한 스크롤이 가능한 소셜 미디어 홈 페이지처럼 디자인하면. 항목 간 여러 가지 다른 장식, 재활용보기를 사용하는 것보다 개별 항목을 많이 제어합니다.

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