Upgrade to Pro — share decks privately, control downloads, hide ads and more …

코틀린 꼭 해야하나요? | 20190405 | 드로이드나이츠2019

코틀린 꼭 해야하나요? | 20190405 | 드로이드나이츠2019

Ted Park

April 05, 2019
Tweet

More Decks by Ted Park

Other Decks in Programming

Transcript

  1. 박상권 - ‘헤이딜러’ 서비스 안드로이드 개발 - ‘박상권의 삽질블로그’ 운영

    (안드로이드/AWS) - Java 오픈소스 대한민국 2위 - 각종 커뮤니티 운영 및 행사 발표 및 주최
  2. 각종 채팅방과 커뮤니티에 올라오는 글들 “코틀린 꼭 해야하나요?” 라고 쓰고

    “코틀린 하기 싫어요” 라고 읽는다 #자매품 - “데이터바인딩 꼭 해야하나요?” - “RxJava 꼭 해야하나요?” - “MVP, MVVM으로 꼭 해야하나요?”
  3. 사전 지식 @Nullable private String address; @NonNull private String id;

    var address: String? = null var id: String = “ted”
  4. 사전 지식 @Nullable private String address; @NonNull private String id;

    var address: String? = null var id: String = “ted” val birthYear: Int = 1986
  5. 사전 지식 @Nullable private String address; @NonNull private String id;

    var address: String? = null var id: String = “ted” val birthYear: Int = 1986 val birthYear = 1986
  6. Safe call - Java private String getSelectedDealerName(@Nullable Car car) {

    if (car == null) { return null; } Auction auction = car.getAuction(); if (auction == null) { return null; } Bid selectedBid = auction.getSelectedBid(); if (selectedBid == null) { return null; } Dealer dealer = selectedBid.getDealer(); if (dealer == null) { return null; } return dealer.getName(); }
  7. Safe call - Java private String getSelectedDealerName(@Nullable Car car) {

    if (car == null) { return null; } Auction auction = car.getAuction(); if (auction == null) { return null; } Bid selectedBid = auction.getSelectedBid(); if (selectedBid == null) { return null; } Dealer dealer = selectedBid.getDealer(); if (dealer == null) { return null; } return dealer.getName(); }
  8. Safe call - Kotlin private fun getSelectedDealerName(car: Car?): String? {

    return car?.auction?.selectedBid?.dealer?.name }
  9. Safe call - Kotlin private fun getSelectedDealerName(car: Car?): String? {

    return car?.auction?.selectedBid?.dealer?.name }
  10. Class - Java public class Dealer { @Nullable private String

    name; @Nullable private String address; public Dealer(@Nullable String name, @Nullable String address) {...} @Nullable public final String getName() {...} public final void setName(@Nullable String var1) {...} @Nullable public final String getAddress() {...} public final void setAddress(@Nullable String var1) {...} }
  11. Class - Kotlin data class Dealer(var name: String?, var address:

    String?) 심지어 toString(), hashCode(), equals(), copy()까지 모두 알아서 만들어줌 (data class 기준)
  12. String template private void logDealerInfo(@NonNull Dealer dealer) { String name

    = dealer.getName(); String address = dealer.getAddress(); Log.d("ted", "딜러이름: " + name + " , 딜러주소: " + address); }
  13. String template private void logDealerInfo(@NonNull Dealer dealer) { String name

    = dealer.getName(); String address = dealer.getAddress(); Log.d("ted", "딜러이름: " + name + " , 딜러주소: " + address); } String.format(Locale.getDefault(), "딜러이름: %1%s , 딜러주소: %2$s", name, address)
  14. String template private void logDealerInfo(@NonNull Dealer dealer) { String name

    = dealer.getName(); String address = dealer.getAddress(); Log.d("ted", "딜러이름: " + name + " , 딜러주소: " + address); } String.format(Locale.getDefault(), "딜러이름: %1%s , 딜러주소: %2$s", name, address) private fun logDealerInfo(dealer: Dealer){ val name = dealer.name val address = dealer.address Log.d("ted","딜러이름: $name , 딜러주소: $address") }
  15. String template private void logDealerInfo(@NonNull Dealer dealer) { String name

    = dealer.getName(); String address = dealer.getAddress(); Log.d("ted", "딜러이름: " + name + " , 딜러주소: " + address); } String.format(Locale.getDefault(), "딜러이름: %1%s , 딜러주소: %2$s", name, address) private fun logDealerInfo(dealer: Dealer){ val name = dealer.name val address = dealer.address Log.d("ted","딜러이름: $name , 딜러주소: $address") }
  16. Overload - Java public class TedCustomView extends FrameLayout { public

    TedCustomView(@NonNull Context context) {...} public TedCustomView(@NonNull Context context, @Nullable AttributeSet attrs) {...} public TedCustomView(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr) {...} public TedCustomView(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes) {...} }
  17. Overload - Kotlin class TedCustomView @JvmOverloads constructor( context: Context, attrs:

    AttributeSet? = null, defStyleAttr: Int = 0, defStyleRes: Int = 0 ) : FrameLayout(context, attrs, defStyleAttr, defStyleRes) { ... }
  18. Overload - Kotlin class TedCustomView @JvmOverloads constructor( context: Context, attrs:

    AttributeSet? = null, defStyleAttr: Int = 0, defStyleRes: Int = 0 ) : FrameLayout(context, attrs, defStyleAttr, defStyleRes) { ... }
  19. Lambda - Java button.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View

    view) { // 할일하기 } }); Java8을 사용할 경우 button.setOnClickListener(view -> { // 할일하기 });
  20. let private void setDealerName(@Nullable Dealer dealer) { if (dealer !=

    null) { String name = dealer.getName(); // 할일하기 } }
  21. let private void setDealerName(@Nullable Dealer dealer) { if (dealer !=

    null) { String name = dealer.getName(); // 할일하기 } } private fun setDealerName(dealer: Dealer?) { dealer?.let { dealer -> val name = dealer.name // 할일하기 } }
  22. let private void setDealerName(@Nullable Dealer dealer) { if (dealer !=

    null) { String name = dealer.getName(); // 할일하기 } } private fun setDealerName(dealer: Dealer?) { dealer?.let { val name = it.name // 할일하기 } }
  23. let / run - Java private void setDealer(@Nullable Dealer dealer)

    { if(dealer == null){ // 문제발생 }else { String name = dealer.getName(); if(name == null){ // 문제발생 }else{ // 할일하기 } } }
  24. let / run - Java private void setDealer(@Nullable Dealer dealer)

    { if (dealer != null && dealer.getName() != null) { String name = dealer.getName(); // 할일하기 } else { // 문제발생 } }
  25. let / run - Kotlin private fun setDealer(dealer: Dealer?) {

    dealer?.name?.let { // 할일하기 } ?: run { // 문제발생 } }
  26. let / run - Kotlin private fun setDealer(dealer: Dealer?) {

    dealer?.name?.let { // 할일하기 } ?: run { // 문제발생 } }
  27. apply Dealer dealer = new Dealer(); dealer.setName("ted"); dealer.setAddress("서울시 강남구"); dealer.setId("gun0912");

    val dealer = Dealer().apply { name = "ted" address = "서울시 강남구" id = "gun0912" }
  28. apply - Intent private Intent getTedActivityIntent() { Intent intent =

    new Intent(this, TedActivity.class); intent.putExtra(EXTRA_AAA, aaa); intent.putExtra(EXTRA_BBB, bbb); intent.putExtra(EXTRA_CCC, ccc); return intent; }
  29. apply - Intent private Intent getTedActivityIntent() { Intent intent =

    new Intent(this, TedActivity.class); intent.putExtra(EXTRA_AAA, aaa); intent.putExtra(EXTRA_BBB, bbb); intent.putExtra(EXTRA_CCC, ccc); return intent; } private fun getTedActivityIntent() = Intent(this, TedActivity::class.java).apply { putExtra(EXTRA_AAA, aaa) putExtra(EXTRA_BBB, bbb) putExtra(EXTRA_CCC, ccc) }
  30. run - RecyclerView private fun initRecyclerView() { binding.recyclerView.run { adapter

    = recyclerViewAdapter layoutManager = GridLayoutManager(context, SPAN_COUNT) addItemDecoration(DividerItemDecoration(context, LinearLayout.VERTICAL)) isNestedScrollingEnabled = false } }
  31. Java코드와의 호환 - Kotlin에서 만들고 class ForJava(var name: String, val

    birth: Int, var isShow: Boolean) - Java에서 사용 String name = forJava.getName(); forJava.setName("ted"); int birth = forJava.getBirth(); boolean isShow = forJava.isShow(); forJava.setShow(true);
  32. Java코드와의 호환 - Kotlin으로 작성된 코드는 Java에서 원래의 사용행태처럼 사용할

    수 있다 - 이런 Annotation을 이용 @JvmName @JvmField @JvmStatic @JvmOverloads 외 등등
  33. Extension function 원래 정의되어있던 함수인것처럼 사용 fun Context.showToast(text: CharSequence, duration:

    Int = Toast.LENGTH_SHORT) { Toast.makeText(this, text, duration).show() } fun Context.startCallActivity(callNumber: String) { val intent = Intent(Intent.ACTION_DIAL) val uri = "tel:$callNumber" intent.data = Uri.parse(uri) startActivity(intent) } showToast("안녕하세요") startCallActivity("01012345678")
  34. 그외 더 유용하고 좋은 키워드들을 검색해서 알아보세요 - 함수형 프로그래밍(Functional

    programming) - 다양한 Collection관련 함수들(kotlin.collections): 예) listOf(1, 2, 3) - Lazy execution(Sequences) 등등
  35. 코틀린 시작하기 - 학습 전 이렇게 공부했어요 1. 공식 홈페이지

    2. 스택오버플로우 3. 미디엄 및 블로그 4. 알고싶거나 찾고 싶은 개념에 대해서 ‘kotlin xxx’ 검색
  36. 코틀린 시작하기 - 코틀린 변환 코틀린 변환 기능으로 바로 변환해보기

    - [Code] -> [Convert Java File to Kotlin File] - 단순변환이기 때문에 코틀린이지만 자바코드스럽게 짜여져 있는경우에 대해서는 보완 필요 (그래도 코틀린으로 변환해준게 어디야..)
  37. 코틀린 시작하기 하지만 피쳐와 리팩토링사이의 중도를 잘 지켜야 하는 현업개발..

    현재 사내 안드로이드 팀 코틀린 코드 작성 규칙 - 새로운 코드는 코틀린으로 작성 - 피쳐개발로 인해 기존코드를 수정해야할경우, 간단한 코드면 함께 kotlin으로 변환 - 여유가 될때마다 kotlin코드로 리팩토링
  38. 코틀린을 자바처럼 코딩하지 말자 val name = bid!!.dealer!!.name val address

    = bid!!.dealer!!.address val intent = Intent(this, TedActivity::class.java) intent.putExtra(EXTRA_AAA, aaa); intent.putExtra(EXTRA_BBB, bbb); intent.putExtra(EXTRA_CCC, ccc); Log.d("ted", "딜러이름: " + name + " , 딜러주소:" + address)
  39. 코틀린을 자바처럼 코딩하지 말자 val name = bid!!.dealer!!.name val address

    = bid!!.dealer!!.address val intent = Intent(this, TedActivity::class.java) intent.putExtra(EXTRA_AAA, aaa); intent.putExtra(EXTRA_BBB, bbb); intent.putExtra(EXTRA_CCC, ccc); Log.d("ted", "딜러이름: " + name + " , 딜러주소:" + address) - 일부는 IDE에서 warning으로 cleanup 가능하도록 도와주고 - 여러 코틀린 키워드들을 학습하면서 조금씩 개선됨 - 다른사람에게 코드를 리뷰받는게 제일 좋고 발전할 수 있음