Activitats

Descomposició d'un problema: muntant mobles

L’objectiu d’aquesta activitat és aprendre a usar el disseny descendent per estructurar un problema general senzill, sense que estigui vinculat a la creació d’un programa.

Descomponeu mitjançant disseny descendent el procés de creació i muntatge d’un moble d’estanteries (suposeu que sou el fuster). Useu al menys dos nivells de descomposició. Intenteu trobar subproblemes repetits en diverses parts del procés.

Nota: Tingueu en compte que el resultat d’aplicar disseny descendent sobre un problema pot variar segons com es plantegi la descomposició. Per tant, les solucions proposades són només una de diverses possibilitats que es podrien considerar correctes. De totes maneres, tingueu en compte que aquesta tècnica no només serveix per fer subdividir un programa en blocs de codi curts, sinó també per fer-lo més fàcil d’entendre.

Descomposició d'un problema: com fer farina

L’objectiu d’aquesta activitat és aprendre a usar el disseny descendent per estructurar un problema general senzill, sense que estigui vinculat a la creació d’un programa.

Descomponeu mitjançant disseny descendent el procés pel qual, partint de llavors de blat, s’arriba a tenir farina.

Nota: Tingueu en compte que el resultat d’aplicar disseny descendent sobre un problema pot variar segons com es plantegi la descomposició. Per tant, les solucions proposades són només una de diverses possibilitats que es podrien considerar correctes. De totes maneres, tingueu en compte que aquesta tècnica no només serveix per fer subdividir un programa en blocs de codi curts, sinó també per fer-lo més fàcil d’entendre.

La frase amb més lletres 'a'

L’objectiu d’aquesta activitat és aprendre a usar el disseny descendent per estructurar un problema senzill i generar el programa que el resol.

Feu un programa anomenat FraseAmbMesAs que vagi llegint frases pel teclat i, en acabar cada entrada d’una frase, mostri quina és la frase que s’ha escrit fins al moment amb més lletres ‘a’ (minúscula o majúscula) i quantes en tenia. El programa ha d’anar-se executant fins a llegir la frase “fi”. A mode de guia de sortida hauria de ser semblant a la que es mostra tot seguit.

  1. Escriu una frase:
  2. > Hola que tal
  3. La frase amb més 'a' és: "Hola què tal"
  4. 2 'a'.
  5. Escriu una frase:
  6. > Aquesta té més 'a'
  7. La frase amb més 'a' és: "Aquesta té més a"
  8. 3 'a'.
  9. Escriu una frase:
  10. > Menys 'a'
  11. La frase amb més 'a' és: "Aquesta té més a"
  12. 3 'a'.
  13. Escriu una frase:
  14. > fi
  15. La frase amb més 'a' és: "Aquesta té més a"
  16. 3 'a'.
  17. (El programa acaba)

  1. import java.util.Scanner;
  2.  
  3. public class ParaulaMesAs {
  4.  
  5. private boolean fi = false;
  6. private int numAs = 0;
  7. private String fraseMesAs = null;
  8. private String fraseActual = null;
  9.  
  10. public static void main (String[] args) {
  11. ParaulaMesAs programa = new ParaulaMesAs();
  12. programa.inici();
  13. }
  14.  
  15. public void inici() {
  16. while(!fi) {
  17. processarFrase();
  18. mostrarResultatActual();
  19. }
  20.  
  21. }
  22.  
  23. public void processarFrase() {
  24. Scanner lector = new Scanner(System.in);
  25. System.out.print("Escriu una frase:\n> ");
  26. fraseActual = lector.nextLine();
  27. if (fraseActual.equals("fi")) {
  28. fi = true;
  29. } else {
  30. compararAs();
  31. }
  32. }
  33.  
  34. public void mostrarResultatActual() {
  35. System.out.print("La frase amb més a's és: ");
  36. System.out.println("\"" + fraseMesAs + "\"");
  37. System.out.println("Té " + numAs + " a's.");
  38. }
  39.  
  40. public void compararAs() {
  41. int acumulador = 0;
  42. String fraseMinuscula = fraseActual.toLowerCase();
  43. for(int i = 0; i < fraseActual.length(); i++) {
  44. if (fraseMinuscula.charAt(i) == 'a') {
  45. acumulador++;
  46. }
  47. }
  48. if (acumulador > numAs) {
  49. numAs = acumulador;
  50. fraseMesAs = fraseActual;
  51. }
  52. }
  53.  
  54. }

Nota: Tingueu en compte que el resultat d’aplicar disseny descendent sobre un problema pot variar segons com es plantegi la descomposició. Per tant, les solucions proposades són només una de diverses possibilitats que es podrien considerar correctes. De totes maneres, tingueu en compte que aquesta tècnica no només serveix per fer subdividir un programa en blocs de codi curts, sinó també per fer-lo més fàcil d’entendre.

Histograma de tirades de dau

L’objectiu d’aquesta activitat és aprendre a usar el disseny descendent per estructurar un problema i generar el programa que el resol.

Feu un programa anomenat GenerarHistograma que mostri l’histograma de totes les tirades possibles amb dos daus de sis cares. Per fer això, l’estratègia que s’ha considerat és desar dins d’un array el nombre de repeticions de cada tirada possible (sempre entre 2 i 12) i després treballar a partir d’aquests valors. A continuació, ha de dir quin valor de tirada és el que té més repeticions. A mode de guia, la sortida hauria de ser semblant a la que es mostra tot seguit:

 2: *
 3: **
 4: ***
 5: ****
 6: *****
 7: ******
 8: *****
 9: ****
10: ***
11: **
12: *
El màxim és 7.

  1. public class GenerarHistograma {
  2.  
  3. public static final int CARES_DAU = 6;
  4.  
  5. //Variable global
  6. int[] llistaTirades = new int[CARES_DAU*2 -1];
  7.  
  8. public static void main (String[] args) {
  9. GenerarHistograma programa = new GenerarHistograma();
  10. programa.inici();
  11. }
  12.  
  13. public void inici() {
  14. generarTirades();
  15. mostrarHistograma();
  16. mostrarMaxim();
  17. }
  18.  
  19. public void generarTirades() {
  20. for(int i = 1; i <= CARES_DAU; i++) {
  21. for(int j = 1; j <= CARES_DAU; j++) {
  22. llistaTirades[i + j - 2]++;
  23. }
  24. }
  25. }
  26.  
  27. public void mostrarHistograma() {
  28. for(int i = 0; i < llistaTirades.length; i++) {
  29. if (i < 8) {
  30. System.out.print(" ");
  31. }
  32. System.out.print( (i + 2) + ": ");
  33. for(int j = 0; j < llistaTirades[i]; j++) {
  34. System.out.print("*");
  35. }
  36. System.out.println();
  37. }
  38. }
  39.  
  40. public void mostrarMaxim() {
  41. int maxim = 0;
  42. for(int i = 1; i < llistaTirades.length; i++) {
  43. if (llistaTirades[i] > llistaTirades[maxim]) {
  44. maxim = i;
  45. }
  46. }
  47. System.out.println("El maxim es " + (maxim + 2) + ".");
  48. }
  49.  
  50. }

Nota: Tingueu en compte que el resultat d’aplicar disseny descendent sobre un problema pot variar segons com es plantegi la descomposició. Per tant, les solucions proposades són només una de diverses possibilitats que es podrien considerar correctes. De totes maneres, tingueu en compte que aquesta tècnica no només serveix per fer subdividir un programa en blocs de codi curts, sinó també per fer-lo més fàcil d’entendre.

Probabilitat de tirades de dau

L’objectiu d’aquesta activitat és codificar un programa partint d’una descomposició donada de l’aplicació de disseny descendent.

Feu un programa anomenat CalculTirada que calculi la probabilitat en tant per cent de treure per sota d’un valor concret tirant dos daus de sis cares. Per fer això, l’estratègia que s’ha considerat és desar dins d’un array el nombre de repeticions de cada tirada possible (sempre entre 2 i 12) i després treballar a partir d’aquests valors, sabent que:

  • Probabilitat de treure 2: suma del nombre de tirades que valen 2 * 100 / 36.
  • Probabilitat de treure 3 o menys: suma del nombre de tirades que valen 2 o 3 * 100 / 36.
  • Probabilitat de treure 4 o menys: suma del nombre de tirades que valen 2 o 3 o 4 * 100 / 36.
  • etc.

Es parteix de la descomposició del problema següent, que haureu de seguir per codificar-lo:

  1. Llegir el valor.
    • Processar entrada pel teclat.
    • Comprovar si està entre 2 i 12.
  2. Generar tirades.
  3. Calcular probabilitat.

A mode de guia, la sortida hauria de ser més o menys com es mostra tot seguit:

Escriu el valor a calcular [2 - 12].
18
El valor no és entre 2 i 12.
5
La probabilitat es 27.0%.

  1. import java.util.Scanner;
  2.  
  3. public class CalculTirada {
  4.  
  5. public static final int CARES_DAU = 6;
  6.  
  7. //Variables globals
  8. int[] llistaTirades = new int[CARES_DAU*2 -1];
  9. int valor = 0;
  10.  
  11. public static void main (String[] args) {
  12. CalculTirada programa = new CalculTirada();
  13. programa.inici();
  14. }
  15.  
  16. public void inici() {
  17. llegirValor();
  18. generarTirades();
  19. mostrarProbabilitat();
  20. }
  21.  
  22. public void llegirValor() {
  23. System.out.println("Escriu el valor a calcular [2 - 12].");
  24. Scanner lector = new Scanner(System.in);
  25. while (valor == 0) {
  26. if (lector.hasNextInt()) {
  27. valor = lector.nextInt();
  28. comprovarValor();
  29. } else {
  30. lector.next();
  31. }
  32. }
  33. lector.nextLine();
  34. }
  35.  
  36. public void generarTirades() {
  37. for(int i = 1; i <= CARES_DAU; i++) {
  38. for(int j = 1; j <= CARES_DAU; j++) {
  39. llistaTirades[i + j - 2]++;
  40. }
  41. }
  42. }
  43.  
  44. public void mostrarProbabilitat() {
  45. int acumulador = 0;
  46. for (int i = 0; i <= (valor - 2); i++) {
  47. acumulador = acumulador + llistaTirades[i];
  48. }
  49. double resultat = (acumulador*100)/ (CARES_DAU*CARES_DAU) ;
  50. System.out.println("La probabilitat es " + resultat + "%.");
  51.  
  52. }
  53.  
  54. public void comprovarValor() {
  55. if ((valor < 2)||(valor > CARES_DAU*2)) {
  56. System.out.println("El valor no es entre 2 i 12.");
  57. valor = 0;
  58. }
  59. }
  60.  
  61. }

Nota: Tingueu en compte que el resultat d’aplicar disseny descendent sobre un problema pot variar segons com es plantegi la descomposició. Per tant, les solucions proposades són només una de diverses possibilitats que es podrien considerar correctes. De totes maneres, tingueu en compte que aquesta tècnica no només serveix per fer subdividir un programa en blocs de codi curts, sinó també per fer-lo més fàcil d’entendre.

Gestor de notes

L’objectiu d’aquesta activitat és dur a terme el procés complet de descomposició d’un problema aplicant disseny descendent per generar un programa de cert grau de complexitat.

Feu un programa anomenat GestorNotes que permeti gestionar les notes dins una aula de fins a 40 estudiants. Les notes es poden anar introduint dins el sistema de manera esglaonada. A partir d’un menú, s’ha de poder:

  • Registrar noves notes. Cada cop que es faci, s’ha de poder llegir una seqüència de valors arbitràriament llarga fins a trobar un -1. Llavors s’acaba la lectura. Per exemple, si es volen entrar les notes 3, 4 i 7.5, s’escriuria “3 4 7,5 -1”.
  • Mostrar per pantalla la nota mitjana fins al moment.
  • Mostrar un histograma de tots les notes segons les classificacions Suspès (menys de 5), Aprovat (entre 5 i 6.5), Notable (entre 6.5 i 8.5) i Excel·lent (més de 8.5).

A mode de guia, tot seguit es mostra una possible sortida en executar el programa. Noteu com, en afegir una segona tanda de notes (només un 10 extra), varien la mitjana i l’histograma de manera correcta.

  1. Benvingut al gestor de notes
  2. ----------------------------
  3. [RT] Registrar notes.
  4. [MJ] Consultar nota mitjana.
  5. [HT] Histograma de notes.
  6. [FI] Sortir.
  7. Opció: RT
  8. Escriu les notes, posa -1 per acabar:
  9. 1 3 3,7 4,4 5 5,6 6,3 7 9 -1
  10.  
  11. Benvingut al gestor de notes
  12. ----------------------------
  13. [RT] Registrar notes.
  14. [MJ] Consultar nota mitjana.
  15. [HT] Histograma de notes.
  16. [FI] Sortir.
  17. Opció: HT
  18. Suspès :****
  19. Aprovat :***
  20. Notable :*
  21. Excel·lent:*
  22.  
  23. Benvingut al gestor de notes
  24. ----------------------------
  25. [RT] Registrar notes.
  26. [MJ] Consultar nota mitjana.
  27. [HT] Histograma de notes.
  28. [FI] Sortir.
  29. Opció: MJ
  30. La nota mitjana és de 5.0.
  31.  
  32. Benvingut al gestor de notes
  33. ----------------------------
  34. [RT] Registrar notes.
  35. [MJ] Consultar nota mitja.
  36. [HT] Histograma de notes.na
  37. [FI] Sortir.
  38. Opció: RT
  39. Escriu les notes, posa -1 per acabar:
  40. 10 -1
  41.  
  42. Benvingut al gestor de notes
  43. ----------------------------
  44. [RT] Registrar notes.
  45. [MJ] Consultar nota mitjana.
  46. [HT] Histograma de notes.
  47. [FI] Sortir.
  48. Opció: HT
  49. Suspès :****
  50. Aprovat :***
  51. Notable :*
  52. Excel·lent:**
  53.  
  54. Benvingut al gestor de notes
  55. ----------------------------
  56. [RT] Registrar notes.
  57. [MJ] Consultar nota mitjana.
  58. [HT] Histograma de notes.
  59. [FI] Sortir.
  60. Opció: MJ
  61. La nota mitjana és de 5.5.
  62.  
  63. Benvingut al gestor de notes
  64. ----------------------------
  65. [RT] Registrar notes.
  66. [MJ] Consultar nota mitjana.
  67. [HT] Histograma de notes.
  68. [FI] Sortir.
  69. Opció: FI

  1. import java.util.Scanner;
  2.  
  3. public class GestorNotes {
  4.  
  5. //1 3 4,5 5 5,5 6 6 7,3 8,5 9,2 10 -1
  6.  
  7. //Constant que tradueix índexs histograma a text
  8. private static final String[] textHistograma =
  9. {"Suspès ", "Aprovat ", "Notable ", "Excel·lent"};
  10.  
  11. //Variables globals
  12. private boolean fi = false;
  13. private boolean seguirLlegint = true;
  14.  
  15. Scanner lector = new Scanner(System.in);
  16. private int numNotes = 0;
  17. private float[] notes = new float[40];
  18.  
  19. //Índexs: 0 = Suspesos, 1 = Aprovats, 2 = Notables, 3 = Excel·lents
  20. private int[] histograma = new int[textHistograma.length];
  21.  
  22.  
  23.  
  24. //Mètodes associats al problema general
  25.  
  26. public static void main (String[] args) {
  27. GestorNotes programa = new GestorNotes();
  28. programa.inici();
  29. }
  30.  
  31. public void inici() {
  32. while (!fi) {
  33. mostrarMenu();
  34. tractarOpcio();
  35. }
  36. }
  37.  
  38. public void mostrarMenu() {
  39. System.out.println("Benvingut al gestor de notes");
  40. System.out.println("----------------------------");
  41. System.out.println("[RT] Registrar notes.");
  42. System.out.println("[MJ] Consultar nota mitjana.");
  43. System.out.println("[HT] Histograma de notes.");
  44. System.out.println("[FI] Sortir.");
  45. System.out.print("Opció: ");
  46. }
  47.  
  48. public void tractarOpcio() {
  49. String opcio = lector.nextLine();
  50. if (opcio.equalsIgnoreCase("RT")) {
  51. registreNotes();
  52. } else if (opcio.equalsIgnoreCase("MJ")) {
  53. mostrarMitjana();
  54. } else if (opcio.equalsIgnoreCase("HT")) {
  55. mostrarHistograma();
  56. } else if (opcio.equalsIgnoreCase("FI")) {
  57. fi = true;
  58. } else {
  59. System.out.println("Opció incorrecta!\n");
  60. }
  61. }
  62.  
  63.  
  64. //Mètodes associats al segon nivell de descomposició
  65.  
  66. public void registreNotes() {
  67. System.out.println("Escriu les notes, posa -1 per acabar:");
  68. while (seguirLlegint) {
  69. if (numNotes == notes.length) {
  70. System.out.println("Ja no queda més espai.");
  71. seguirLlegint = false;
  72. }
  73. llegirValor();
  74. }
  75. lector.nextLine();
  76. }
  77.  
  78. public void mostrarMitjana() {
  79. if (numNotes > 0) {
  80. System.out.print("La nota mitjana és de ");
  81. calculaMitjana();
  82. System.out.println(".");
  83. } else {
  84. System.out.println("No hi ha notes registrades.");
  85. }
  86. }
  87.  
  88. public void mostrarHistograma() {
  89. calculaHistograma();
  90. for(int i = 0; i < histograma.length; i++) {
  91. System.out.print(textHistograma[i] + ":");
  92. for (int j = 0; j < histograma[i]; j++) {
  93. System.out.print("*");
  94. }
  95. System.out.println();
  96. }
  97. }
  98.  
  99. //Mètodes associats al tercer nivell de descomposició
  100.  
  101. public void llegirValor() {
  102. if (lector.hasNextFloat()) {
  103. float valor = lector.nextFloat();
  104. if (valor == -1) {
  105. seguirLlegint = false;
  106. } else {
  107. notes[numNotes] = valor;
  108. numNotes++;
  109. }
  110. } else {
  111. lector.next();
  112. }
  113. }
  114.  
  115. public void calculaMitjana() {
  116. float acumulador = 0;
  117. for(int i = 0; i < numNotes; i++) {
  118. acumulador = acumulador + notes[i];
  119. }
  120. System.out.print((acumulador / numNotes));
  121. }
  122.  
  123. public void calculaHistograma() {
  124. for (int i = 0; i < numNotes; i++) {
  125. if ((notes[i] >= 9)&&(notes[i] <= 10)) {
  126. histograma[3]++;
  127. } else if (notes[i] >= 6.5) {
  128. histograma[2]++;
  129. } else if (notes[i] >= 5) {
  130. histograma[1]++;
  131. } else {
  132. histograma[0]++;
  133. }
  134. }
  135. }
  136.  
  137. }

Nota: Tingueu en compte que el resultat d’aplicar disseny descendent sobre un problema pot variar segons com es plantegi la descomposició. Per tant, les solucions proposades són només una de diverses possibilitats que es podrien considerar correctes. De totes maneres, tingueu en compte que aquesta tècnica no només serveix per fer subdividir un programa en blocs de codi curts, sinó també per fer-lo més fàcil d’entendre.

Anar a la pàgina anterior:
Descomposició de problemes
Anar a la pàgina següent:
Exercicis d'autoavaluació