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

Lis mon code

9fe8f69ed3f442b205816ce9af169529?s=47 dicaormu
October 02, 2021

Lis mon code

Si vous êtes un développeur, peut-être que vous vous demandez comment mieux écrire le code pour qu'il soit fonctionnel, efficace, correct et plus facile à comprendre.
Avec ce talk, je vais me concentrer sur des règles et concepts de la psychologie avec des exemples concrets sur le code, pour trouver les paramètres généraux, qui nous aident à identifier le code qui est lisible par rapport au code qui ne l'est pas.

9fe8f69ed3f442b205816ce9af169529?s=128

dicaormu

October 02, 2021
Tweet

Transcript

  1. 1 Lis mon code Ou pourquoi c’est important d’écrire du

    code lisible
  2. 2 Diana Ortega Développeur back-end avec plusieurs années d'expérience dans

    l'écosystème JVM et le langage Go. Vécu de nombreux projets cloud et data et passionnée par le développement logiciel, la Data et le craftsmanship @dicaormu
  3. 3 • Introduction et contexte • Mémoire à long terme

    • Mémoire de travail • Modèles mentaux Agenda
  4. 4 Introduction

  5. 5 Pourquoi t'en soucies-tu ?

  6. 6 • D’habitude on travaille sur des projets avec une

    base de code existante • En 2013 la quantité des lignes de code estimés était de 1 trillion (Grady Booch's keynote at AOSD) • Il y a plus de 190M de projets gitHub dans le monde (d’après octoverse), dont de projets open source On lit beaucoup de code
  7. 7 90% du travail d’un développeur consiste à lire du

    code
  8. 8 La plupart des logiciels sont développés par des équipes

    8
  9. 9 Contexte

  10. 10 Test 1 : Code Scala

  11. 11 case class ArgumentDefaultConf(env: String, mvt_cpt: Float, uwx2: Int, QUSCRTUS:

    String, i: Int, fs: FileSystemService, SK_tt1: String, toto: String, fab11: String, colv2: String, csvHeaderFromExtendedReader: String = "false" ) Test 1
  12. 12 Combien de variables vous vous rappelez ?

  13. 13 Nombre magique

  14. 14 D’après les recherches, la quantité d’information que le cerveau

    peut faire face avant que la confusion ne s'installe, est connue comme le nombre magique George Miller 1956 - psychologue Américain et Gordon Parker 2012 4
  15. 15 Test 2 : Code Java

  16. 16 class Volume{ int width, height, length, posx, posy, posz,

    time; String color, name; Float spin, velocity; public int computeAngularVelocity(){ …. } } Test 2
  17. 17 De quelles variables vous vous rappelez ?

  18. 18 De quelles variables vous vous rappelez du premier test

    ?
  19. 19 public static void mian(String[] args) { Volume v =

    new Volume(); System.out.println(v.computeAngularVelocity()); } } 19 C’est possible que vous ne vous rappelez de l'implémentation dans quelques quelques heures
  20. 20 Mémoire à long terme

  21. 21 public static void mian(String[] args) { Volume v =

    new Volume(); System.out.println(v.computeAngularVelocity()); } }
  22. 22 Test 3 : Code Java

  23. 23 a) for (String car : cars){ i) System.out.println(car); }

    b) for (int i=0; i<cars.size(); i++){ i) System.out.println(cars.get(i)); } c) for (int i = 0; cars.size()-1 >= i; i=i+1){ i) System.out.println(cars.get(i)); } Quelle est la meilleure option ?
  24. 24 Si c’était un langage inconnu A) for (String car

    : cars){…}
  25. 25 A) for (String car : cars){…} // il y

    a le mot clé for, alors c’est une boucle Si c’était un langage inconnu
  26. 26 A) for (String car : cars){…} // il y

    a le mot clé for, alors c’est une boucle // On déclare la variable car Si c’était un langage inconnu
  27. 27 A) for (String car : cars){…} // il y

    a le mot clé for, alors c’est une boucle // On déclare la variable car // et on parcourt la collection de cars // pour mettre chaque élément dans la variable car Si c’était un langage inconnu
  28. 28 A) for (String car : cars){…} // Itérer sur

    la liste de cars. Et on connaît le type de car Langage connu
  29. 29 C) for(int i = 0; cars.size()-1 >= i; i=i+1){...}

    // il faut faire tout le processus Langage connu, code non idiomatique
  30. 30 for (String car : cars){ …} Idiomatique code, standards

    et patterns : existent dans tous les langages
  31. 31 cars.flatMap(_...)) Idiomatique code, standards et patterns : existent dans

    tous les langages
  32. 32 const ( C0 = iota C1 C2 ) Idiomatique

    code, standards et patterns : existent dans tous les langages
  33. 33 defmodule ComputerBuilder do … end Idiomatique code, standards et

    patterns : existent dans tous les langages
  34. 34 • Utilisation de patterns • Utilisation de code idiomatique

    • Séparation par couches • Standards du langage • Familiarité => à quoi sert un flat map ? Reconnaissance des formes
  35. 35 • Noms de variables • Noms de méthodes •

    Noms de packages • Formatage du code • Interaction entre les services Cohérence
  36. 36 Il y a des compromis à faire

  37. 37 Pour faciliter le travail des devs, il faut automatiser

  38. 38 De quelles variables vous vous rappelez du test 2

    ?
  39. 39 Mémoire de travail ou comment le cerveau organise l’information

    ?
  40. 40 4

  41. 41 Test 4 : Code Go

  42. 42 fruitsColors := map[string]string{"apple": "red", "banana": "yellow"} for key, value

    := range fruitsColors { fmt.Printf("%s -> %s\n", key, value) } if fruitsColors["apple"] == "red" { goodFruit = "apple" } else { goodFruit = "banana" }
  43. 43 que fait ce code ?

  44. 44 fruitsColors:=map[string]string{"apple": "red", "banana": "yellow"} for key,value:=range fruitsColors{ fmt.Printf("%s ->

    %s\n",key,value) } if fruitsColors["apple"]=="red"{ goodFruit="apple" } else{ goodFruit="banana" }
  45. 45 que fait ce code ?

  46. 46 fruitsColors := map[string]string{ "apple": "red", "banana": "yellow"} for key,

    value := range fruitsColors { fmt.Printf("%s -> %s\n", key, value) } if fruitsColors["apple"] == "red" { goodFruit = "apple" } else { goodFruit = "banana" }
  47. 47 que fait ce code ?

  48. 48 Les espaces sont aussi du code

  49. 49 • Séparer les idées à l'intérieur d’une méthode avec

    des espaces • Chaque méthode implémente peu d’idées • Utiliser les éléments du langage comme les interfaces ou les classes • Utiliser des packages (attention aux noms) • Evitez d’avoir un grand package “utils” Regroupement
  50. 50

  51. 51 from Ivan Daniluk blog - Rethinking Visual Programming

  52. 52 Explication très superficielle de Cowan, Nelson (1995) attention and

    memory : an integrated framework
  53. 53 Focus d’attention Explication très superficielle de Cowan, Nelson (1995)

    attention and memory : an integrated framework
  54. 54 fruitsColors := map[string]string{ "apple": "red", "banana": "yellow"} Explication très

    superficielle de Cowan, Nelson (1995) attention and memory : an integrated framework
  55. 55 for key, value := range fruitsColors { fmt.Printf("%s ->

    %s\n", key, value) } Explication très superficielle de Cowan, Nelson (1995) attention and memory : an integrated framework
  56. 56 if fruitsColors["apple"] == "red" { goodFruit = "apple" }

    Explication très superficielle de Cowan, Nelson (1995) attention and memory : an integrated framework
  57. 57 else { goodFruit = "banana" } Explication très superficielle

    de Cowan, Nelson (1995) attention and memory : an integrated framework
  58. 58 func function2(goodFruit string) { Explication très superficielle de Cowan,

    Nelson (1995) attention and memory : an integrated framework
  59. 59 Explication très superficielle de Cowan, Nelson (1995) attention and

    memory : an integrated framework
  60. 60

  61. 61 Seulement 10% du temps, un développeur est capable de

    reprendre son code en moins d’une minute après une interruption Takao Nakagawa et al., “Quantifying Programmers’ Mental Workload during Program Comprehension Based on Cerebral Blood Flow Measurement: A Controlled Experiment,” 2014
  62. 62 Il est nécessaire de limiter la dispersion de notre

    attention
  63. 63 Arbitrage entre Essayer de réduire la quantité d’interactions de

    mon code Essayer d’avoir tout mon code dans un seul endroit
  64. 64 Arbitrage entre largeur profondeur

  65. 65 picture: https://www.hitwest.com/news/le-rock-balancing-a-son-festival-34267

  66. 66 Il faut réduire la charge cognitive

  67. 67 Long parameter list Switch statements Alternative classes with different

    interfaces Primitive obsession Incomplete library class Large class Lazy class Data class Temporary field Data clumps Divergent change Feature envy Inappropriate intimacy Duplicated code or code clones Comments Message chains Middle man Parallel inheritance Refused bequest Shotgun surgery Speculative generality Les code smells- Martin Fowler
  68. 68 Modèles mentaux ou comment le cerveau peut résoudre les

    problèmes ?
  69. 69 val brands= cars.map(_.brand) case class Car(brand: String, km: Long...)

    Afficher les marques des voitures Problème
  70. 70 names.. ??? Additionner le kilométrage par marque Problème

  71. 71 Test 5 : No code Philip Johnson-Laird, Princeton-1983

  72. 72 72 1. 2.

  73. 73 Aidez votre mémoire de travail

  74. 74 • Un diagramme d’état peut nous aider à comprendre

    un système • Un diagramme d’architecture du code peut nous aider à comprendre le code et nous aider à réduire la charge cognitive Modèles sketch by Nagai Hideyuki http://www.anopticalillusion.com/2015/06/impossible-stairway-by-nagai-hideyu ki/
  75. 75 • On peut se baser sur des approches existantes

    pour générer nos modèles: ◦ Domain Driven Design (DDD) ◦ Architectures hexagonales Modèles pour les systèmes plus complexes sketch by Nagai Hideyuki http://www.anopticalillusion.com/2015/06/impossible-stairway-by-nagai-hideyuki/
  76. 76 Séparer l'apprentissage du domain de l’exploration du code

  77. 77 Pour nous aider à coder notre modèle: Test Driven

    Development (TDD) 77
  78. 78

  79. 79

  80. 80 Exemple 6 : Code Elixir

  81. 81 def up do alter table(:articles) do add :search_vector, :tsvector

    end execute "CREATE INDEX article_search_index ON articles USING GIN(search_vector)" end Exemple Elixir
  82. 82 • Si vous n’êtes pas dev. Elixir, vous traduisez

    ce code : def up do : création d’un méthode alter table(:articles) do : modification de la table articles … execute "CREATE INDEX article_search_index ON articles USING GIN(search_vector)" : C’est du SQL
  83. 83 • Si vous n’êtes pas dev. Elixir, vous traduisez

    ce code : def up do : création d’un méthode alter table(:articles) do : modification de la table articles … execute "CREATE INDEX article_search_index ON articles USING GIN(search_vector)" : C’est du SQL On mélange 2 types d’abstraction!!!
  84. 84 • Du code lisible est un code avec un

    modèle fort • Evitez les dépendances cycliques et les code smells • Evitez de mélanger les abstractions • Aidez votre mémoire Comment réduire la charge cognitive?
  85. 85 Conclusion

  86. 86 Make it work, make it right, make it fast

    Kent Beck (co-inventeur du xp)
  87. 87 Make it right ⇒ lisibilité

  88. 88 • Nous avons une charge cognitive limitée (4 +-

    2) • On peut mieux exploiter ce petit nombre Conclusion
  89. 89 Cohérence

  90. 90 Regroupement

  91. 91 Equilibre

  92. 92 Modèles mentaux

  93. 93 Analyse

  94. 94 De quelles variables vous vous rappelez du test 2

    ?
  95. 95 Questions ? @Xebiconfr - #Xebicon19

  96. 96 Références • GopherCon Europe 2019: Egon Elbre - Psychology

    of Code Readability • Octoverse survey • Cowan, Nelson (1995) attention and memory : an integrated framework • University of New South Wales. "Four is the 'magic' number." ScienceDaily. ScienceDaily, 28 November 2012. • Raymond Lister, Toward a Developmental Epistemology of Computer Programming; WiPSCE '16 • Felienne Hermans, The Programmer's Brain, What every programmer needs to know about cognition