Java Notes

switch Example - Random Insults

The following class could be useful for generating random insults in response to erroneous user input.

Source code formatting. Some of the cases are formatted on a single line. This is a common style when they do similar short actions. It makes the switch statements much easier to read.

Separate model (logic) from user interface. This program is separated into two classes: one contains the logic (or "model" as it's more often called) for generating an insult as a string. It knows nothing about the user interface, and could equally well be used in a dialog program (as in the test program below), console I/O, a GUI program, or a web-based application.

Random Insult Model

This is the logic of the program, and does no I/O so it would be equally suitable as the logic behind a console program, GUI program, or web server program.

  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 
 32 
 33 
 34 
 35 
 36 
 37 
 38 
 39 
 40 
 41 
 42 
 43 
 44 
 45 
 46 
 47 
 48 
 49 
 50 
 51 
 52 
 53 
 54 
 55 
 56 
 57 
 58 
 59 
 60 
 61 
 62 
 63 
 64 
 65 
 66 
 67 
 68 
 69 
 70 
 71 
 72 
 73 
 74 
 75 
 76 
 77 
 78 
 79 
 80 
 81 
 82 
 83 
 84 
 85 
 86 
 87 
 88 
 89 
 90 
 91 
 92 
 93 
 94 
 95 
 96 
 97 
 98 
 99 
100 
101 
102 
103 
104 
105 
// File   : flow-switch/insult/InsultGenerator1.java
// Purpose: Generates random insults.
// Author : Fred Swartz  2006 Aug 23  Placed in public domain
// Comments: This switch statements were written in the 
//           most conservative style -- a default clause
//           and no returns in them.
//
//           The structure of the random generation is
//           entirely in executable code,
//           A much better way to write this is as a
//           data-Driven program, where this information is
//           represented by data structures, with a
//           simple program to process the data.
//
//           The data-driven style allows the data to be
//           read in from user-editable files for example,
//           so the program need not be recompiled for changes.

public class InsultGenerator1 {

    //============================================ badInputInsult
    public static String badInputInsult() {
        String insult;
        switch (rand(2)) {
            case 0: insult = "What kind of "
                      + infoAdjective() + " "
                      + infoNoun()
                      + " is this, you "
                      + personAdjective() + " "
                      + person()
                      + "?";
                      break;

            case 1: insult = "Never enter this kind of "
                      + infoAdjective() + " "
                      + infoNoun()
                      + " again!!!!";
                      break;
                      
            default:insult = "Oops -- bad switch statement";
        }
        return insult;
    }

    //==================================================== person
    private static String person() {
        String name;
        switch (rand(3)) {
            case 0 : name = "idiot"   ; break;
            case 1 : name = "imbecile"; break;
            case 2 : name = "moron"   ; break;
            default: name = "bad value from person???";
        }
        return name;
    }

    //=========================================== personAdjective
    private static String personAdjective() {
        String adj;
        switch (rand(4)) {
            case 0 : adj = "clueless"; break;
            case 1 : adj = "witless" ; break;
            case 2 : adj = "stupid"  ; break;
            case 3:  adj = "hopeless"; break;
            default: adj = "bad value from infoAdjective???";
        }
        return adj;
    }

    //============================================= infoAdjective
    private static String infoAdjective() {
        String adj;
        switch (rand(5)) {
            case 0: adj = "revolting"  ; break;
            case 1: adj = "insulting"  ; break;
            case 2: adj = "meaningless"; break;
            case 3: adj = "useless"    ; break;
            case 4: adj = "idiotic"    ; break;
            default:adj = "bad value from infoAdjective???";
        }
        return adj;
    }

    //================================================== infoNoun
    private static String infoNoun() {
    	String noun;
        switch (rand(4)) {
            case 0: noun = "nonsense"; break;
            case 1: noun = "crap"    ; break;
            case 2: noun = "swill"   ; break;
            case 3: noun = "garbage" ; break;
            default:noun = "bad value from infoNoun???";
        }
        return noun;
    }

    //===================================================== rand
    // Utility method to generate random numbers in range 0..bound-1.
    // Starting the range at zero was simply to match the typical
    // Java ranges (eg, switch, subscripts) that start at zero.
    // Returns random int in range 0...bound-1
    private static int rand(int bound) {
        return (int) (Math.random() * bound);
    }
}

Main program

  1 
  2 
  3 
  4 
  5 
  6 
  7 
  8 
  9 
 10 
 11 
 12 
 13 
 14 
 15 
 16 
 17 
// File   : flow-switch/insult/TestTextGenerator1.java
// Purpose: Show some random insults.
// Author : Fred Swartz
// License: public domain
// Date   : 2006 May 3

import javax.swing.*;

public class TestTextGenerator1 {
    public static void main(String[] args) {
        String display;
        do {
            display = InsultGenerator1.badInputInsult()
                    + "\n\nWould you like another opinion?";
        } while (JOptionPane.showConfirmDialog(null, display) == JOptionPane.YES_OPTION);
    }
}

Data-driven programming

Replace methods with data structure? This version is written with executable Java code. It is usually very desirable to replace executable code with some kind of data structure. There are several reasons for this.

Programming problems

  1. Problem (using arrays): Get rid of the methods, and replace them with arrays of strings. You'll find it useful to define a method to choose a random element from an array of Strings. To keep this problem simple don't read the data in from files. It might look like
       private static String chooseRandom(String[] words)
       
  2. Problem (using Map and File I/O): Another way to think about this problem is to have a special syntax to denote something that should be replaced -- I'll use "angle brackets" to surround terms that should be replaced by a something that is dynamically generated. For example, the starting element could be the string "<insult>".

    The program would then look up the definition of "insult" in something like HashMap<String, ArrayList<String>> and randomly choose one of the strings from the array list. For example, it might replace "<insult>" with "Never enter this kind of <infoAdj> <infoNoun> again!!!!"

    The program would then find each thing surrounded by angle brackets and replace it with a randomly chosen values from its associated arrays. This process is repeated until all angle bracketted symbols have been replaced.

    Read data in from a file. One plausible format would be to have the the "meta-symbols" start in column 1, and all possible definitions follow on lines that start with a blank. For example,

    <insult>
        Never enter this kind of <infoAdj> <infoNoun> again!!!!
        What kind of <infoAdj> <infoNoun> is this, you <personAdj> <person>?
        
    <infoAdj>
        revolting
        insulting
        meaningless
        useless
        idiotic
    . . .