Pertemuan 9: Desain World of Zuul

Tugas Pertemuan 9

Nama: Farrel Aqilla Novianto

NRP: 5025241015

Kelas: Pemrograman Berorientasi Objek (A)

Source Code

World of Zuul

Pada tugas ini dilakukan analisis desain kelas (class design) terhadap program game World of Zuul. Analisis difokuskan pada dua aspek penting dalam rekayasa perangkat lunak, yaitu Cohesion dan Coupling.

Cohesion (Kohesi)

Kohesi menggambarkan sejauh mana tanggung jawab dan fungsi di dalam suatu kelas saling berkaitan secara logis. Sebuah kelas dikatakan memiliki high cohesion (kohesi tinggi) apabila seluruh metodenya berfokus pada satu tujuan atau tanggung jawab utama. Sebaliknya, low cohesion (kohesi rendah) terjadi bila satu kelas menangani banyak hal yang tidak berhubungan, sehingga sulit dipelihara dan diperluas. Dengan kata lain, kohesi yang tinggi menunjukkan bahwa kelas tersebut “berdiri sendiri” dan hanya melakukan hal yang memang menjadi perannya, tanpa mencampur urusan kelas lain.

Coupling (Kopling)

Kopling menunjukkan seberapa kuat ketergantungan antar kelas dalam sebuah sistem. Program yang baik memiliki low coupling (kopling longgar), artinya perubahan pada satu kelas tidak akan menimbulkan efek besar pada kelas lainnya. Sebaliknya, high coupling (kopling erat) berarti kelas-kelas saling bergantung, sehingga jika satu bagian diubah, bagian lain juga harus disesuaikan. Kopling yang longgar memudahkan proses pemeliharaan (maintenance) dan pengembangan (scalability) program.

Secara umum, desain program World of Zuul yang baik seharusnya memiliki high cohesion dan low coupling, sehingga setiap kelas memiliki satu tanggung jawab yang jelas dan hubungan antar kelasnya tidak terlalu erat.

Kode Game.java

/**
 *
 * @author Farrel Aqilla Novianto
 */
public class Game{
    private Parser parser;
    private Room currentRoom;

    public Game(){
        createRoom();
        parser = new Parser();
    }

    private void createRoom(){
        Room outside, theater, pub, lab, office;
        outside = new Room("outside the main entrance of the university");
        theater = new Room("in a lecture theater");
        pub = new Room("in the campus pub");
        lab = new Room("in a computing lab");
        office = new Room("in the computing admin office");
        outside.setExits(null, theater, lab, pub);
        theater.setExits(null, null, null, outside);
        pub.setExits(null, outside, null, null);
        lab.setExits(outside, office, null, null);
        office.setExits(null, null, null, lab);
        currentRoom = outside;
    }

    private void printWelcome(){
        System.out.println();
        System.out.println("Welcome to Adventure!");
        System.out.println("Adventure is a new, incredibly boring adventure game.");
        System.out.println("Type 'help' if you need help.");
        System.out.println();
        System.out.println("You are " + currentRoom.getDescription());
        System.out.println("Exits: ");
        if(currentRoom.northExit != null){
            System.out.println("north");
        }
        if(currentRoom.eastExit != null){
            System.out.println("east");
        }
        if(currentRoom.southExit != null){
            System.out.println("south");            
        }
        if(currentRoom.westExit != null){
            System.out.println("west");
        }
    }

    private void printHelp(){
        System.out.println("You are lost. You are alone. You wander");
        System.out.println("around at the university.");
        System.out.println();
        System.out.println("Your command words are:");
        System.out.println("[go <direction>] - [quit] - [help]");
    }

    private boolean quit(Command command){
        if(command.hasSecondWord()){
            System.out.println("Quit what?");
            return false;
        }
        return true;
    }

    private void goRoom(Command command){
        if(!command.hasSecondWord()){
            System.out.println("Go where?");
            return;
        }
        String direction = command.getSecondWord();
        Room nextRoom = null;
        if(direction.equals("north")){
            nextRoom = currentRoom.northExit;
        }
        if(direction.equals("east")){
            nextRoom = currentRoom.eastExit;
        }
        if(direction.equals("south")){
            nextRoom = currentRoom.southExit;
        }
        if(direction.equals("west")){
            nextRoom = currentRoom.westExit;
        }
        if(nextRoom == null){
            System.out.println("There is no door!");
        }
        else{
            currentRoom = nextRoom;
            System.out.println("You are " + currentRoom.getDescription());
            System.out.println("Exits:");
            if(currentRoom.northExit != null){
               System.out.println("north"); 
            }   
            if(currentRoom.eastExit != null){
                System.out.println("east");
            }
            if(currentRoom.southExit != null){
                System.out.println("south");
            }
            if(currentRoom.westExit != null){
                System.out.println("west");
            }
            System.out.println();
        }
    }
    
    private boolean processCommand(Command command){
        boolean wantToQuit = false;
        if(command.isUnknown()){
            System.out.println("I don't know what you mean...");
            return false;
        }
        String commandWord = command.getCommandWord();
        if(commandWord.equals("help")) printHelp();
        else if(commandWord.equals("go")) goRoom(command);
        else if(commandWord.equals("quit")) wantToQuit = quit(command);
        return wantToQuit;
    }

    public void play(){
        printWelcome();
        boolean finished = false;
        while(!finished){
            Command command = parser.getCommand();
            finished = processCommand(command);
        }
        System.out.println("Thank you for playing. Good bye!");
    }
}

Kode Command.java

/**
 *
 * @author Farrel Aqilla Novianto
 */
public class Command{
    private String commandWord;
    private String secondWord;

    public Command(String firstWord, String secondWord){
        commandWord = firstWord;
        this.secondWord = secondWord;
    }

    public String getCommandWord(){
        return commandWord;
    }

    public String getSecondWord(){
        return secondWord;
    }

    public boolean isUnknown(){
        return (commandWord == null);
    }

    public boolean hasSecondWord(){
        return (secondWord != null);
    }
}

Kode CommandWords.java
/**
 *
 * @author Farrel Aqilla Novianto
 */
public class CommandWords{
    private static final String[] validCommands = { "go", "quit", "help" };
    
    public CommandWords(){}
    public boolean isCommand(String str){
        for(int i = 0; i < validCommands.length; i++){
            if(validCommands[i].equals(str)){
                 return true;   
            }
        }
        return false;
    }
}

Kode Room.java
/**
 *
 * @author Farrel Aqilla Novianto
 */
public class Room{
    private String description;
    public Room northExit;
    public Room eastExit;
    public Room southExit;
    public Room westExit;

    public Room(String description){
        this.description = description;
    }

    public void setExits(Room north, Room east, Room south, Room west){
        if(north != null){
            northExit = north;
        }
        if(east != null){
           eastExit = east; 
        }
        if(south != null){
           southExit = south; 
        }
        if(west != null){
            westExit = west;
        }
    }

    public String getDescription(){
        return description;
    }
}

Kode Parser.java
/**
 *
 * @author Farrel Aqilla Novianto
 */
import java.util.StringTokenizer;
import java.io.InputStreamReader;
import java.io.BufferedReader;

public class Parser{
    private CommandWords commands;

    public Parser(){
        commands = new CommandWords();
    }

    public Command getCommand(){
        String inputLine = "";
        String word1 = null, word2 = null;
        System.out.print("> ");
        BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
        try{
            inputLine = reader.readLine();
        } 
        catch(java.io.IOException exc){
            System.out.println("There was an error during reading: " + exc.getMessage());
        }
        StringTokenizer tokenizer = new StringTokenizer(inputLine);
        if(tokenizer.hasMoreTokens()){
            word1 = tokenizer.nextToken();
        }
        if(tokenizer.hasMoreTokens()){
            word2 = tokenizer.nextToken();
        }
        if(commands.isCommand(word1)){
            return new Command(word1, word2);
        } 
        else{
            return new Command(null, word2);
        }
    }
}

Dokumentasi


Kesimpulan

Berdasarkan hasil analisis terhadap desain kelas pada program World of Zuul, dapat disimpulkan bahwa kualitas desain perangkat lunak sangat dipengaruhi oleh tingkat cohesion dan coupling antar kelas.

Program dengan high cohesion menunjukkan bahwa setiap kelas memiliki tanggung jawab yang jelas dan terfokus pada satu fungsi utama, sehingga kode menjadi lebih mudah dipahami, diuji, serta dipelihara. Sementara itu, low coupling memastikan hubungan antar kelas bersifat longgar, sehingga perubahan pada satu kelas tidak menimbulkan efek besar terhadap kelas lain.

Dengan menerapkan prinsip high cohesion dan low coupling, struktur program World of Zuul dapat menjadi lebih modular, fleksibel, dan efisien dalam pengembangan maupun pengelolaan di masa mendatang. Prinsip ini juga membantu menjaga stabilitas sistem saat dilakukan penambahan fitur atau modifikasi logika permainan.

Komentar

Postingan populer dari blog ini

Final Project: Tetris

Pertemuan 4: Membuat Clock Display