initial commit

This commit is contained in:
2024-05-06 01:38:39 +02:00
commit 7ac35f607a
450 changed files with 10976 additions and 0 deletions

View File

@@ -0,0 +1,59 @@
package oop.ch01.chess1;
import java.util.ArrayList;
class Board {
ArrayList<Piece> pieces;
Board() {
this.pieces = new ArrayList<Piece>();
}
void add(Piece piece) {
if (piece.board != this)
throw new IllegalArgumentException("wrong board");
final Piece existing = this.pieceAt(piece.row, piece.col);
if (existing != null)
throw new IllegalArgumentException("already occupied by " +
existing.toString());
this.pieces.add(piece);
}
void printBoard() {
System.out.println(" 1 2 3 4 5 6 7 8");
System.out.println(" +---+---+---+---+---+---+---+---+");
for (int row = 1; row <= 8; row++) {
System.out.print("" + row + " ");
for (int col = 1; col <= 8; col++) {
final Piece p = this.pieceAt(row, col);
final char c = p == null ? ' ' : p.charRep();
System.out.print("| " + c + " ");
}
System.out.println("|");
System.out.println(" +---+---+---+---+---+---+---+---+");
}
}
Piece pieceAt(int row, int col) {
for (Piece p : this.pieces)
if (p.row == row && p.col == col)
return p;
return null;
}
void check() {
for (Piece p1 : this.pieces) {
System.out.println(p1.toString());
for (Piece p2 : this.pieces)
if (p1 != p2)
if (p1.canCapture(p2))
System.out.println(" can capture " + p2.toString());
else
System.out.println(" cannot capture " + p2.toString());
}
}
public String toString() {
return "pieces: " + this.pieces;
}
}

View File

@@ -0,0 +1,15 @@
package oop.ch01.chess1;
class Chess {
public static void main(String[] args) {
final Board board = new Board();
final Piece p1 = new Piece(Kind.queen, Color.black, board, 1, 4);
final Piece p2 = new Piece(Kind.queen, Color.white, board, 8, 4);
final Piece p3 = new Piece(Kind.knight, Color.white, board, 3, 3);
final Piece p4 = new Piece(Kind.knight, Color.black, board, 6, 4);
System.out.println(board);
System.out.println(board.toString());
board.printBoard();
board.check();
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch01.chess1;
enum Color {
black, white
}

View File

@@ -0,0 +1,5 @@
package oop.ch01.chess1;
enum Kind {
queen, knight
}

View File

@@ -0,0 +1,87 @@
package oop.ch01.chess1;
import static java.lang.Integer.signum;
import static java.lang.Math.abs;
class Piece {
Kind kind;
Color color;
Board board;
int row;
int col;
Piece(Kind kind, Color color, Board board, int row, int col) {
if (row < 1 || row > 8 || col < 1 || col > 8)
throw new IllegalArgumentException("Invalid pos " + row + "/" + col);
this.kind = kind;
this.color = color;
this.board = board;
this.row = row;
this.col = col;
board.add(this);
}
char charRep() {
return switch (this.kind) {
case queen -> this.queenCharRep();
case knight -> this.knightCharRep();
};
}
public String toString() {
return switch (this.kind) {
case queen -> this.queenToString();
case knight -> this.knightToString();
};
}
boolean canCapture(Piece other) {
return switch (this.kind) {
case queen -> this.queenCanCapture(other);
case knight -> this.knightCanCapture(other);
};
}
char queenCharRep() {
return this.color == Color.white ? 'q' : 'Q';
}
char knightCharRep() {
return this.color == Color.white ? 'n' : 'N';
}
String queenToString() {
return "" + this.color + " queen at (" + this.row + ", " + this.col + ")";
}
String knightToString() {
return "" + this.color + " knight at (" + this.row + ", " + this.col + ")";
}
boolean queenCanCapture(Piece other) {
if (this.board != other.board || this.color == other.color)
return false;
if (other.row != this.row &&
other.col != this.col &&
abs(other.row - this.row) != abs(other.col - this.col))
return false;
final int dr = signum(other.row - this.row);
final int dc = signum(other.col - this.col);
int r = this.row + dr;
int c = this.col + dc;
while (r != other.row || c != other.col) {
if (this.board.pieceAt(r, c) != null) return false;
r += dr;
c += dc;
}
return true;
}
boolean knightCanCapture(Piece other) {
if (this.board != other.board || this.color == other.color)
return false;
final int dr = abs(this.row - other.row);
final int dc = abs(this.col - other.col);
return dr == 2 && dc == 1 || dr == 1 && dc == 2;
}
}

View File

@@ -0,0 +1,4 @@
/**
* Using objects with methods for the Java solution of the chess problem.
*/
package oop.ch01.chess1;

View File

@@ -0,0 +1,59 @@
package oop.ch01.chess2;
import java.util.ArrayList;
class Board {
ArrayList<Piece> pieces;
Board() {
this.pieces = new ArrayList<Piece>();
}
void add(Piece piece) {
if (piece.board != this)
throw new IllegalArgumentException("wrong board");
final Piece existing = pieceAt(piece.row, piece.col);
if (existing != null)
throw new IllegalArgumentException("already occupied by " +
existing.toString());
pieces.add(piece);
}
void printBoard() {
System.out.println(" 1 2 3 4 5 6 7 8");
System.out.println(" +---+---+---+---+---+---+---+---+");
for (int row = 1; row <= 8; row++) {
System.out.print("" + row + " ");
for (int col = 1; col <= 8; col++) {
final Piece p = pieceAt(row, col);
final char c = p == null ? ' ' : p.charRep();
System.out.print("| " + c + " ");
}
System.out.println("|");
System.out.println(" +---+---+---+---+---+---+---+---+");
}
}
Piece pieceAt(int row, int col) {
for (Piece p : pieces)
if (p.row == row && p.col == col)
return p;
return null;
}
void check() {
for (Piece p1 : pieces) {
System.out.println(p1.toString());
for (Piece p2 : pieces)
if (p1 != p2)
if (p1.canCapture(p2))
System.out.println(" can capture " + p2.toString());
else
System.out.println(" cannot capture " + p2.toString());
}
}
public String toString() {
return pieces.toString();
}
}

View File

@@ -0,0 +1,15 @@
package oop.ch01.chess2;
class Chess {
public static void main(String[] args) {
final Board board = new Board();
final Piece p1 = new Piece(Kind.queen, Color.black, board, 1, 4);
final Piece p2 = new Piece(Kind.queen, Color.white, board, 8, 4);
final Piece p3 = new Piece(Kind.knight, Color.white, board, 3, 3);
final Piece p4 = new Piece(Kind.knight, Color.black, board, 6, 4);
System.out.println(board);
System.out.println(board.toString());
board.printBoard();
board.check();
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch01.chess2;
enum Color {
black, white
}

View File

@@ -0,0 +1,5 @@
package oop.ch01.chess2;
enum Kind {
queen, knight
}

View File

@@ -0,0 +1,87 @@
package oop.ch01.chess2;
import static java.lang.Integer.signum;
import static java.lang.Math.abs;
class Piece {
Kind kind;
Color color;
Board board;
int row;
int col;
Piece(Kind kind, Color color, Board board, int row, int col) {
if (row < 1 || row > 8 || col < 1 || col > 8)
throw new IllegalArgumentException("Invalid pos " + row + "/" + col);
this.kind = kind;
this.color = color;
this.board = board;
this.row = row;
this.col = col;
board.add(this);
}
char charRep() {
return switch (kind) {
case queen -> queenCharRep();
case knight -> knightCharRep();
};
}
public String toString() {
return switch (kind) {
case queen -> queenToString();
case knight -> knightToString();
};
}
boolean canCapture(Piece other) {
return switch (kind) {
case queen -> queenCanCapture(other);
case knight -> knightCanCapture(other);
};
}
char queenCharRep() {
return color == Color.white ? 'q' : 'Q';
}
char knightCharRep() {
return color == Color.white ? 'n' : 'N';
}
String queenToString() {
return "" + color + " queen at (" + row + ", " + col + ")";
}
String knightToString() {
return "" + color + " knight at (" + row + ", " + col + ")";
}
boolean queenCanCapture(Piece other) {
if (board != other.board || color == other.color)
return false;
if (other.row != row &&
other.col != col &&
abs(other.row - row) != abs(other.col - col))
return false;
final int dr = signum(other.row - row);
final int dc = signum(other.col - col);
int r = row + dr;
int c = col + dc;
while (r != other.row || c != other.col) {
if (board.pieceAt(r, c) != null) return false;
r += dr;
c += dc;
}
return true;
}
boolean knightCanCapture(Piece other) {
if (board != other.board || color == other.color)
return false;
final int dr = abs(row - other.row);
final int dc = abs(col - other.col);
return dr == 2 && dc == 1 || dr == 1 && dc == 2;
}
}

View File

@@ -0,0 +1,5 @@
/**
* Using objects with methods for the Java solution of the chess problem.
* Qualification of members with "this." is avoided where possible.
*/
package oop.ch01.chess2;

View File

@@ -0,0 +1,79 @@
package oop.ch02.cards;
/**
* Represents any card with a name and a unique serial number.
*
* @author Mark Minas
*/
public class Card {
/**
* The name of this card.
*/
private final String name;
/**
* Counts the number of instantiations of this class.
*/
private static int counter = 0;
/**
* The unique serial number of this card.
*/
private final int number;
/**
* Creates a new card with the specified name.
*
* @param name the name of this card
*/
public Card(String name) {
if (name == null)
throw new NullPointerException("name is null");
this.name = name;
this.number = ++counter;
}
/**
* Creates a new card for a student with the specified number.
*
* @param num the student's number
*/
public Card(int num) {
this("MatrNr. " + num);
}
/**
* Returns the name of this card.
*
* @return the name
*/
public String getName() {
return name;
}
/**
* Returns the serial number of this card.
*
* @return the serial number
*/
public int getNumber() {
return number;
}
/**
* Returns the number of instantiations of this class.
*
* @return the number of instantiations.
*/
public static int getCounter() {
return counter;
}
/**
* Returns a string representation of this card.
*/
@Override
public String toString() {
return "Card " + name + " (no " + number + ")";
}
}

View File

@@ -0,0 +1,20 @@
package oop.ch02.cards;
import java.util.Arrays;
public class CardExample {
public static void main(String[] args) {
Card c1 = new Card(12345);
System.out.println(c1 + " erstellt.");
String[] names = {"Franz Mueller", "Hans Mustermann", "Peter Meier"};
Card[] cards = new Card[names.length];
for (int i = 0; i < names.length; i++) {
cards[i] = new Card(names[i]);
System.out.println(cards[i] + " erstellt.");
}
System.out.println("cards = " + cards);
System.out.println("cards = " + Arrays.deepToString(cards));
System.out.println("#Card = " + Card.getCounter());
}
}

View File

@@ -0,0 +1,34 @@
package oop.ch02.cards0;
public class Card {
private final String name;
private static int counter = 0;
private final int number;
public Card(String name) {
if (name == null)
throw new NullPointerException("name is null");
this.name = name;
this.number = ++Card.counter;
}
public Card(int num) {
this("MatrNr. " + num);
}
public String getName() {
return name;
}
public int getNumber() {
return number;
}
public static int getCounter() {
return Card.counter;
}
public String toString() {
return "Card " + name + " (no " + number + ")";
}
}

View File

@@ -0,0 +1,59 @@
package oop.ch02.chess1;
import java.util.ArrayList;
public class Board {
private ArrayList<Piece> pieces;
public Board() {
this.pieces = new ArrayList<Piece>();
}
void add(Piece piece) {
if (piece.getBoard() != this)
throw new IllegalArgumentException("wrong board");
final Piece existing = pieceAt(piece.getRow(), piece.getCol());
if (existing != null)
throw new IllegalArgumentException("already occupied by " +
existing.toString());
pieces.add(piece);
}
public void printBoard() {
System.out.println(" 1 2 3 4 5 6 7 8");
System.out.println(" +---+---+---+---+---+---+---+---+");
for (int row = 1; row <= 8; row++) {
System.out.print("" + row + " ");
for (int col = 1; col <= 8; col++) {
final Piece p = pieceAt(row, col);
final char c = p == null ? ' ' : p.charRep();
System.out.print("| " + c + " ");
}
System.out.println("|");
System.out.println(" +---+---+---+---+---+---+---+---+");
}
}
public Piece pieceAt(int row, int col) {
for (Piece p : pieces)
if (p.getRow() == row && p.getCol() == col)
return p;
return null;
}
public void check() {
for (Piece p1 : pieces) {
System.out.println(p1.toString());
for (Piece p2 : pieces)
if (p1 != p2)
if (p1.canCapture(p2))
System.out.println(" can capture " + p2.toString());
else
System.out.println(" cannot capture " + p2.toString());
}
}
public String toString() {
return pieces.toString();
}
}

View File

@@ -0,0 +1,15 @@
package oop.ch02.chess1;
public class Chess {
public static void main(String[] args) {
final Board board = new Board();
final Piece p1 = new Piece(Kind.queen, Color.black, board, 1, 4);
final Piece p2 = new Piece(Kind.queen, Color.white, board, 8, 4);
final Piece p3 = new Piece(Kind.knight, Color.white, board, 3, 3);
final Piece p4 = new Piece(Kind.knight, Color.black, board, 6, 4);
System.out.println(board);
System.out.println(board.toString());
board.printBoard();
board.check();
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch02.chess1;
public enum Color {
black, white
}

View File

@@ -0,0 +1,5 @@
package oop.ch02.chess1;
public enum Kind {
queen, knight
}

View File

@@ -0,0 +1,107 @@
package oop.ch02.chess1;
import static java.lang.Integer.signum;
import static java.lang.Math.abs;
public class Piece {
private Kind kind;
private Color color;
private Board board;
private int row;
private int col;
public Piece(Kind kind, Color color, Board board, int row, int col) {
if (row < 1 || row > 8 || col < 1 || col > 8)
throw new IllegalArgumentException("Invalid pos " + row + "/" + col);
this.kind = kind;
this.color = color;
this.board = board;
this.row = row;
this.col = col;
board.add(this);
}
public Kind getKind() {
return kind;
}
public Color getColor() {
return color;
}
public Board getBoard() {
return board;
}
public int getRow() {
return row;
}
public int getCol() {
return col;
}
public char charRep() {
return switch (kind) {
case queen -> queenCharRep();
case knight -> knightCharRep();
};
}
public String toString() {
return switch (kind) {
case queen -> queenToString();
case knight -> knightToString();
};
}
public boolean canCapture(Piece other) {
return switch (kind) {
case queen -> queenCanCapture(other);
case knight -> knightCanCapture(other);
};
}
private char queenCharRep() {
return color == Color.white ? 'q' : 'Q';
}
private char knightCharRep() {
return color == Color.white ? 'n' : 'N';
}
private String queenToString() {
return "" + color + " queen at (" + row + ", " + col + ")";
}
private String knightToString() {
return "" + color + " knight at (" + row + ", " + col + ")";
}
private boolean queenCanCapture(Piece other) {
if (board != other.board || color == other.color)
return false;
if (other.row != row &&
other.col != col &&
abs(other.row - row) != abs(other.col - col))
return false;
final int dr = signum(other.row - row);
final int dc = signum(other.col - col);
int r = row + dr;
int c = col + dc;
while (r != other.row || c != other.col) {
if (board.pieceAt(r, c) != null) return false;
r += dr;
c += dc;
}
return true;
}
private boolean knightCanCapture(Piece other) {
if (board != other.board || color == other.color)
return false;
final int dr = abs(row - other.row);
final int dc = abs(col - other.col);
return dr == 2 && dc == 1 || dr == 1 && dc == 2;
}
}

View File

@@ -0,0 +1,4 @@
/**
* Using access modifiers in the Java solution of the chess problem.
*/
package oop.ch02.chess1;

View File

@@ -0,0 +1,54 @@
package oop.ch02.chess2;
import java.util.ArrayList;
public class Board {
private final Piece[][] field = new Piece[8][8];
private final ArrayList<Piece> pieces = new ArrayList<Piece>();
void add(Piece piece) {
if (piece.getBoard() != this)
throw new IllegalArgumentException("wrong board");
final Piece existing = pieceAt(piece.getRow(), piece.getCol());
if (existing != null)
throw new IllegalArgumentException("already occupied by " +
existing.toString());
field[piece.getRow() - 1][piece.getCol() - 1] = piece;
pieces.add(piece);
}
public void printBoard() {
System.out.println(" 1 2 3 4 5 6 7 8");
System.out.println(" +---+---+---+---+---+---+---+---+");
for (int row = 1; row <= 8; row++) {
System.out.print("" + row + " ");
for (int col = 1; col <= 8; col++) {
final Piece p = pieceAt(row, col);
final char c = p == null ? ' ' : p.charRep();
System.out.print("| " + c + " ");
}
System.out.println("|");
System.out.println(" +---+---+---+---+---+---+---+---+");
}
}
public Piece pieceAt(int row, int col) {
return field[row - 1][col - 1];
}
public void check() {
for (Piece p1 : pieces) {
System.out.println(p1.toString());
for (Piece p2 : pieces)
if (p1 != p2)
if (p1.canCapture(p2))
System.out.println(" can capture " + p2.toString());
else
System.out.println(" cannot capture " + p2.toString());
}
}
public String toString() {
return pieces.toString();
}
}

View File

@@ -0,0 +1,15 @@
package oop.ch02.chess2;
public class Chess {
public static void main(String[] args) {
final Board board = new Board();
final Piece p1 = new Piece(Kind.queen, Color.black, board, 1, 4);
final Piece p2 = new Piece(Kind.queen, Color.white, board, 8, 4);
final Piece p3 = new Piece(Kind.knight, Color.white, board, 3, 3);
final Piece p4 = new Piece(Kind.knight, Color.black, board, 6, 4);
System.out.println(board);
System.out.println(board.toString());
board.printBoard();
board.check();
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch02.chess2;
public enum Color {
black, white
}

View File

@@ -0,0 +1,5 @@
package oop.ch02.chess2;
public enum Kind {
queen, knight
}

View File

@@ -0,0 +1,107 @@
package oop.ch02.chess2;
import static java.lang.Integer.signum;
import static java.lang.Math.abs;
public class Piece {
private Kind kind;
private Color color;
private Board board;
private int row;
private int col;
public Piece(Kind kind, Color color, Board board, int row, int col) {
if (row < 1 || row > 8 || col < 1 || col > 8)
throw new IllegalArgumentException("Invalid pos " + row + "/" + col);
this.kind = kind;
this.color = color;
this.board = board;
this.row = row;
this.col = col;
board.add(this);
}
public Kind getKind() {
return kind;
}
public Color getColor() {
return color;
}
public Board getBoard() {
return board;
}
public int getRow() {
return row;
}
public int getCol() {
return col;
}
public char charRep() {
return switch (kind) {
case queen -> queenCharRep();
case knight -> knightCharRep();
};
}
public String toString() {
return switch (kind) {
case queen -> queenToString();
case knight -> knightToString();
};
}
public boolean canCapture(Piece other) {
return switch (kind) {
case queen -> queenCanCapture(other);
case knight -> knightCanCapture(other);
};
}
private char queenCharRep() {
return color == Color.white ? 'q' : 'Q';
}
private char knightCharRep() {
return color == Color.white ? 'n' : 'N';
}
private String queenToString() {
return "" + color + " queen at (" + row + ", " + col + ")";
}
private String knightToString() {
return "" + color + " knight at (" + row + ", " + col + ")";
}
private boolean queenCanCapture(Piece other) {
if (board != other.board || color == other.color)
return false;
if (other.row != row &&
other.col != col &&
abs(other.row - row) != abs(other.col - col))
return false;
final int dr = signum(other.row - row);
final int dc = signum(other.col - col);
int r = row + dr;
int c = col + dc;
while (r != other.row || c != other.col) {
if (board.pieceAt(r, c) != null) return false;
r += dr;
c += dc;
}
return true;
}
private boolean knightCanCapture(Piece other) {
if (board != other.board || color == other.color)
return false;
final int dr = abs(row - other.row);
final int dc = abs(col - other.col);
return dr == 2 && dc == 1 || dr == 1 && dc == 2;
}
}

View File

@@ -0,0 +1,4 @@
/**
* Using arrays for speeding up the Java solution of the chess problem.
*/
package oop.ch02.chess2;

View File

@@ -0,0 +1,33 @@
package oop.ch02.clock;
public class Clock1 {
private int hour;
private int minute;
public Clock1(int hour, int minute) {
if (hour < 0 || hour >= 24 || minute < 0 || minute >= 60)
throw new IllegalArgumentException("Invalid time " + hour + ":" + minute);
this.hour = hour;
this.minute = minute;
}
public int getHour() {
return hour;
}
public void setHour(int hour) {
if (hour < 0 || hour >= 24)
throw new IllegalArgumentException("Invalid hour " + hour);
this.hour = hour;
}
public int getMinute() {
return minute;
}
public void setMinute(int minute) {
if (minute < 0 || minute >= 60)
throw new IllegalArgumentException("Invalid minute " + minute);
this.minute = minute;
}
}

View File

@@ -0,0 +1,27 @@
package oop.ch02.clock;
public class Clock2 {
private int hour;
private int minute;
public Clock2(int hour, int minute) {
if (hour < 0 || hour >= 24 || minute < 0 || minute >= 60)
throw new IllegalArgumentException("Invalid time " + hour + ":" + minute);
this.hour = hour;
this.minute = minute;
}
public int getHour() {
return hour;
}
public int getMinute() {
return minute;
}
public void tick() {
minute = (minute + 1) % 60;
if (minute == 0)
hour = (hour + 1) % 24;
}
}

View File

@@ -0,0 +1,24 @@
package oop.ch02.clock;
public class Clock3 {
public static final int MINUTES_PER_DAY = 60 * 24;
private int mins;
public Clock3(int hour, int minute) {
if (hour < 0 || hour >= 24 || minute < 0 || minute >= 60)
throw new IllegalArgumentException("Invalid time " + hour + ":" + minute);
this.mins = 60 * hour + minute;
}
public int getHour() {
return mins / 60;
}
public int getMinute() {
return mins % 60;
}
public void tick() {
mins = (mins + 1) % MINUTES_PER_DAY;
}
}

View File

@@ -0,0 +1,13 @@
package oop.ch02.clock;
public class Example {
public static void main(String[] args) {
Clock3 clock = new Clock3(22, 55);
for (int i = 0; i < 7; i++)
clock.tick();
System.out.printf("%02d:%02d%n", clock.getHour(), clock.getMinute());
for (int i = 0; i < 60; i++)
clock.tick();
System.out.printf("%02d:%02d%n", clock.getHour(), clock.getMinute());
}
}

View File

@@ -0,0 +1,54 @@
package oop.ch03.chess;
import java.util.ArrayList;
public class Board {
private final Piece[][] field = new Piece[8][8];
private final ArrayList<Piece> pieces = new ArrayList<Piece>();
void add(Piece piece) {
if (piece.getBoard() != this)
throw new IllegalArgumentException("wrong board");
final Piece existing = pieceAt(piece.getRow(), piece.getCol());
if (existing != null)
throw new IllegalArgumentException("already occupied by " +
existing.toString());
field[piece.getRow() - 1][piece.getCol() - 1] = piece;
pieces.add(piece);
}
public void printBoard() {
System.out.println(" 1 2 3 4 5 6 7 8");
System.out.println(" +---+---+---+---+---+---+---+---+");
for (int row = 1; row <= 8; row++) {
System.out.print("" + row + " ");
for (int col = 1; col <= 8; col++) {
final Piece p = pieceAt(row, col);
final char c = p == null ? ' ' : p.charRep();
System.out.print("| " + c + " ");
}
System.out.println("|");
System.out.println(" +---+---+---+---+---+---+---+---+");
}
}
public Piece pieceAt(int row, int col) {
return field[row - 1][col - 1];
}
public void check() {
for (Piece p1 : pieces) {
System.out.println(p1.toString());
for (Piece p2 : pieces)
if (p1 != p2)
if (p1.canCapture(p2))
System.out.println(" can capture " + p2.toString());
else
System.out.println(" cannot capture " + p2.toString());
}
}
public String toString() {
return pieces.toString();
}
}

View File

@@ -0,0 +1,17 @@
package oop.ch03.chess;
public class Chess {
public static void main(String[] args) {
final Board board = new Board();
final Piece p1 = new Queen(Color.black, board, 1, 4);
final Piece p2 = new Queen(Color.white, board, 8, 4);
final Piece p3 = new Knight(Color.white, board, 3, 3);
final Piece p4 = new Knight(Color.black, board, 6, 4);
final Piece p5 = new Rook(Color.white, board, 7, 1);
final Piece p6 = new Rook(Color.black, board, 4, 4);
System.out.println(board);
System.out.println(board.toString());
board.printBoard();
board.check();
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch03.chess;
public enum Color {
black, white
}

View File

@@ -0,0 +1,28 @@
package oop.ch03.chess;
import static java.lang.Math.abs;
public class Knight extends Piece {
public Knight(Color color, Board board, int row, int col) {
super(color, board, row, col);
}
@Override
public char charRep() {
return getColor() == Color.white ? 'n' : 'N';
}
@Override
public String toString() {
return "" + getColor() + " knight at (" + getRow() + ", " + getCol() + ")";
}
@Override
public boolean canCapture(Piece other) {
if (getBoard() != other.getBoard() || getColor() == other.getColor())
return false;
final int dr = abs(getRow() - other.getRow());
final int dc = abs(getCol() - other.getCol());
return dr == 2 && dc == 1 || dr == 1 && dc == 2;
}
}

View File

@@ -0,0 +1,38 @@
package oop.ch03.chess;
public abstract class Piece {
private Color color;
private Board board;
private int row;
private int col;
protected Piece(Color color, Board board, int row, int col) {
if (row < 1 || row > 8 || col < 1 || col > 8)
throw new IllegalArgumentException("Invalid pos " + row + "/" + col);
this.color = color;
this.board = board;
this.row = row;
this.col = col;
board.add(this);
}
public Color getColor() {
return color;
}
public Board getBoard() {
return board;
}
public int getRow() {
return row;
}
public int getCol() {
return col;
}
public abstract char charRep();
public abstract boolean canCapture(Piece other);
}

View File

@@ -0,0 +1,40 @@
package oop.ch03.chess;
import static java.lang.Integer.signum;
import static java.lang.Math.abs;
public class Queen extends Piece {
public Queen(Color color, Board board, int row, int col) {
super(color, board, row, col);
}
@Override
public char charRep() {
return getColor() == Color.white ? 'q' : 'Q';
}
@Override
public String toString() {
return "" + getColor() + " queen at (" + getRow() + ", " + getCol() + ")";
}
@Override
public boolean canCapture(Piece other) {
if (getBoard() != other.getBoard() || getColor() == other.getColor())
return false;
if (other.getRow() != getRow() &&
other.getCol() != getCol() &&
abs(other.getRow() - getRow()) != abs(other.getCol() - getCol()))
return false;
final int dr = signum(other.getRow() - getRow());
final int dc = signum(other.getCol() - getCol());
int r = getRow() + dr;
int c = getCol() + dc;
while (r != other.getRow() || c != other.getCol()) {
if (getBoard().pieceAt(r, c) != null) return false;
r += dr;
c += dc;
}
return true;
}
}

View File

@@ -0,0 +1,41 @@
package oop.ch03.chess;
import static java.lang.Integer.signum;
import static java.lang.Math.abs;
public class Rook extends Piece{
public Rook(Color color, Board board, int row, int col){
super(color, board, row, col);
}
@Override
public char charRep(){
return getColor() == Color.white ? 'r' : 'R';
}
@Override
public boolean canCapture(Piece other){
if (getBoard() != other.getBoard() || getColor() == other.getColor()) {
return false;
}
if(other.getRow() != getRow() && other.getCol() != getCol()){
return false;
}
final int dr = signum(other.getRow() - getRow());
final int dc = signum(other.getCol() - getCol());
int r = getRow() + dr;
int c = getCol() + dc;
while (r != other.getRow() || c != other.getCol()) {
if (getBoard().pieceAt(r, c) != null) {
return false;
}
r += dr;
c += dc;
}
return true;
}
}

View File

@@ -0,0 +1,4 @@
/**
* Using inheritance and dynamic binding in the Java solution of the chess problem.
*/
package oop.ch03.chess;

View File

@@ -0,0 +1,26 @@
package oop.ch03.vehicles;
import java.util.List;
public class AmphibienBsp {
public static void main(String[] args) {
final Auto golf = new AutoImpl(500);
final Schiff titanic = new SchiffImpl(53150E3);
final Amphibienfahrzeug alligator = new AmphibienfahrzeugImpl(750, 8000);
System.out.println("Fahrzeuge:");
final List<Fahrzeug> fahrzeuge = List.of(golf, titanic, alligator);
for (Fahrzeug fz : fahrzeuge)
System.out.println(fz + ", zuladung: " + fz.getMaxZuladung());
System.out.println("Autos:");
final List<Auto> autos = List.of(golf, alligator);
for (Auto auto : autos)
System.out.println(auto + ", zuladung: " + auto.getMaxZuladung());
System.out.println("Schiffe:");
final List<Schiff> schiffe = List.of(titanic, alligator);
for (Schiff schiff : schiffe)
System.out.println(schiff + ", zuladung: " + schiff.getMaxZuladung());
}
}

View File

@@ -0,0 +1,3 @@
package oop.ch03.vehicles;
public interface Amphibienfahrzeug extends Auto, Schiff {}

View File

@@ -0,0 +1,27 @@
package oop.ch03.vehicles;
public class AmphibienfahrzeugImpl extends AutoImpl implements Amphibienfahrzeug {
private final SchiffImpl schiff;
public AmphibienfahrzeugImpl(double maxAutoZuladung,
double maxSchiffZuladung) {
super(maxAutoZuladung);
this.schiff = new SchiffImpl(maxSchiffZuladung);
}
@Override
public boolean kannHierFahren(double laenge, double breite) {
return super.kannHierFahren(laenge, breite) ||
schiff.kannHierFahren(laenge, breite);
}
@Override
public double getMaxZuladung() {
return Math.max(super.getMaxZuladung(), schiff.getMaxZuladung());
}
@Override
public double getTiefgang() {
return schiff.getTiefgang();
}
}

View File

@@ -0,0 +1,27 @@
package oop.ch03.vehicles;
public class AmphibienfahrzeugImpl2 extends SchiffImpl implements Amphibienfahrzeug {
private final AutoImpl auto;
public AmphibienfahrzeugImpl2(double maxAutoZuladung,
double maxSchiffZuladung) {
super(maxSchiffZuladung);
this.auto = new AutoImpl(maxAutoZuladung);
}
@Override
public boolean kannHierFahren(double laenge, double breite) {
return super.kannHierFahren(laenge, breite) ||
auto.kannHierFahren(laenge, breite);
}
@Override
public double getMaxZuladung() {
return Math.max(super.getMaxZuladung(), auto.getMaxZuladung());
}
@Override
public double getAchslast() {
return auto.getAchslast();
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch03.vehicles;
public interface Auto extends Fahrzeug {
double getAchslast();
}

View File

@@ -0,0 +1,22 @@
package oop.ch03.vehicles;
public class AutoImpl extends FahrzeugImpl implements Auto {
public AutoImpl(double maxZuladung) {
super(maxZuladung);
}
@Override
public double getAchslast() {
return maxZuladung;
}
@Override
public boolean kannHierFahren(double laenge, double breite) {
return aufStrasse(laenge, breite) && getGewicht() < maxZuladung;
}
private boolean aufStrasse(double laenge, double breite) {
// TODO implement
return false;
}
}

View File

@@ -0,0 +1,9 @@
package oop.ch03.vehicles;
public interface Fahrzeug {
double getGewicht();
double getMaxZuladung();
boolean kannHierFahren(double laenge, double breite);
}

View File

@@ -0,0 +1,20 @@
package oop.ch03.vehicles;
public abstract class FahrzeugImpl implements Fahrzeug {
protected final double maxZuladung;
protected FahrzeugImpl(double maxZuladung) {
this.maxZuladung = maxZuladung;
}
@Override
public double getGewicht() {
// TODO implement
return 1000.;
}
@Override
public double getMaxZuladung() {
return maxZuladung;
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch03.vehicles;
public interface Schiff extends Fahrzeug {
double getTiefgang();
}

View File

@@ -0,0 +1,23 @@
package oop.ch03.vehicles;
public class SchiffImpl extends FahrzeugImpl implements Schiff {
public SchiffImpl(double maxZuladung) {
super(maxZuladung);
}
@Override
public double getTiefgang() {
// TODO implement
return 1.;
}
@Override
public boolean kannHierFahren(double laenge, double breite) {
return aufWasser(laenge, breite) && getGewicht() < maxZuladung;
}
private boolean aufWasser(double laenge, double breite) {
// TODO implement
return false;
}
}

View File

@@ -0,0 +1,27 @@
package oop.ch04.equality;
import oop.ch04.equality.card1.Card;
public class Example {
public static void main(String[] args) {
Card c1 = new Card("foo");
Card c2 = new Card("foo");
System.out.println(c1 == c2);
int i1 = 42;
int i2 = 2 * 21;
System.out.println(i1 == i2);
double f1 = 0.5;
double f2 = 1.0 / 2.0;
System.out.println(f1 == f2);
String s1 = "OOP";
String s2 = "O" + "OP";
System.out.println(s1 == s2);
String s3 = "OOP".substring(1);
String s4 = "OP";
System.out.println(s3 == s4);
}
}

View File

@@ -0,0 +1,89 @@
package oop.ch04.equality.card1;
/**
* Represents any card with a name and a unique serial number.
*
* @author Mark Minas
*/
public class Card {
/**
* The name of this card.
*/
private final String name;
/**
* Counts the number of instantiations of this class.
*/
private static int counter = 0;
/**
* The unique serial number of this card.
*/
private final int number;
/**
* Creates a new card with the specified name.
*
* @param name the name of this card
*/
public Card(String name) {
if (name == null)
throw new NullPointerException("name is null");
this.name = name;
this.number = ++counter;
}
/**
* Creates a new card for a student with the specified number.
*
* @param num the student's number
*/
public Card(int num) {
this("MatrNr. " + num);
}
/**
* Returns the name of this card.
*
* @return the name
*/
public String getName() {
return name;
}
/**
* Returns the serial number of this card.
*
* @return the serial number
*/
public int getNumber() {
return number;
}
/**
* Returns the number of instantiations of this class.
*
* @return the number of instantiations.
*/
public static int getCounter() {
return counter;
}
/**
* Returns a string representation of this card.
*/
@Override
public String toString() {
return "Card " + name + " (no " + number + ")";
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o instanceof Card) {
final Card that = (Card) o;
return this.name.equals(that.name);
}
return false;
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch04.equality.card1;
public enum Color {
red, green, blue
}

View File

@@ -0,0 +1,26 @@
package oop.ch04.equality.card1;
public class ColoredCard extends Card {
public final Color color;
public ColoredCard(String key, Color color) {
super(key);
this.color = color;
}
@Override
public String toString() {
return color + " " + super.toString();
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o instanceof ColoredCard) {
final ColoredCard that = (ColoredCard) o;
return this.color == that.color &&
super.equals(that);
}
return false;
}
}

View File

@@ -0,0 +1,11 @@
package oop.ch04.equality.card1;
public class Example {
public static void main(String[] args) {
Card k1 = new Card("foo");
Card c1 = new ColoredCard("foo", Color.green);
System.out.println(c1.equals(k1));
System.out.println(k1.equals(c1));
}
}

View File

@@ -0,0 +1,89 @@
package oop.ch04.equality.card2;
/**
* Represents any card with a name and a unique serial number.
*
* @author Mark Minas
*/
public class Card {
/**
* The name of this card.
*/
private final String name;
/**
* Counts the number of instantiations of this class.
*/
private static int counter = 0;
/**
* The unique serial number of this card.
*/
private final int number;
/**
* Creates a new card with the specified name.
*
* @param name the name of this card
*/
public Card(String name) {
if (name == null)
throw new NullPointerException("name is null");
this.name = name;
this.number = ++counter;
}
/**
* Creates a new card for a student with the specified number.
*
* @param num the student's number
*/
public Card(int num) {
this("MatrNr. " + num);
}
/**
* Returns the name of this card.
*
* @return the name
*/
public String getName() {
return name;
}
/**
* Returns the serial number of this card.
*
* @return the serial number
*/
public int getNumber() {
return number;
}
/**
* Returns the number of instantiations of this class.
*
* @return the number of instantiations.
*/
public static int getCounter() {
return counter;
}
/**
* Returns a string representation of this card.
*/
@Override
public String toString() {
return "Card " + name + " (no " + number + ")";
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o instanceof Card) {
final Card that = (Card) o;
return this.name.equals(that.name);
}
return false;
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch04.equality.card2;
public enum Color {
red, green, blue
}

View File

@@ -0,0 +1,28 @@
package oop.ch04.equality.card2;
public class ColoredCard extends Card {
public final Color color;
public ColoredCard(String key, Color color) {
super(key);
this.color = color;
}
@Override
public String toString() {
return color + " " + super.toString();
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o instanceof ColoredCard) {
final ColoredCard that = (ColoredCard) o;
return this.color == that.color &&
super.equals(that);
}
if (o instanceof Card)
return o.equals(this);
return false;
}
}

View File

@@ -0,0 +1,15 @@
package oop.ch04.equality.card2;
public class Example {
public static void main(String[] args) {
Card k1 = new Card("foo");
Card c1 = new ColoredCard("foo", Color.green);
Card c2 = new ColoredCard("foo", Color.red);
System.out.println(c1.equals(k1));
System.out.println(k1.equals(c1));
System.out.println(c2.equals(k1));
System.out.println(k1.equals(c2));
System.out.println(c1.equals(c2));
}
}

View File

@@ -0,0 +1,89 @@
package oop.ch04.equality.card3;
/**
* Represents any card with a name and a unique serial number.
*
* @author Mark Minas
*/
public class Card {
/**
* The name of this card.
*/
private final String name;
/**
* Counts the number of instantiations of this class.
*/
private static int counter = 0;
/**
* The unique serial number of this card.
*/
private final int number;
/**
* Creates a new card with the specified name.
*
* @param name the name of this card
*/
public Card(String name) {
if (name == null)
throw new NullPointerException("name is null");
this.name = name;
this.number = ++counter;
}
/**
* Creates a new card for a student with the specified number.
*
* @param num the student's number
*/
public Card(int num) {
this("MatrNr. " + num);
}
/**
* Returns the name of this card.
*
* @return the name
*/
public String getName() {
return name;
}
/**
* Returns the serial number of this card.
*
* @return the serial number
*/
public int getNumber() {
return number;
}
/**
* Returns the number of instantiations of this class.
*
* @return the number of instantiations.
*/
public static int getCounter() {
return counter;
}
/**
* Returns a string representation of this card.
*/
@Override
public String toString() {
return "Card " + name + " (no " + number + ")";
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o instanceof Card) {
final Card that = (Card) o;
return this.name.equals(that.name) && this.getClass() == that.getClass();
}
return false;
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch04.equality.card3;
public enum Color {
red, green, blue
}

View File

@@ -0,0 +1,25 @@
package oop.ch04.equality.card3;
public class ColoredCard extends Card {
public final Color color;
public ColoredCard(String key, Color color) {
super(key);
this.color = color;
}
@Override
public String toString() {
return color + " " + super.toString();
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o instanceof ColoredCard) {
final ColoredCard that = (ColoredCard) o;
return this.color == that.color && super.equals(that);
}
return false;
}
}

View File

@@ -0,0 +1,15 @@
package oop.ch04.equality.card3;
public class Example {
public static void main(String[] args) {
Card k1 = new Card("foo");
Card c1 = new ColoredCard("foo", Color.green);
Card c2 = new ColoredCard("foo", Color.red);
System.out.println(c1.equals(k1));
System.out.println(k1.equals(c1));
System.out.println(c2.equals(k1));
System.out.println(k1.equals(c2));
System.out.println(c1.equals(c2));
}
}

View File

@@ -0,0 +1,93 @@
package oop.ch04.equality.card4;
/**
* Represents any card with a name and a unique serial number.
*
* @author Mark Minas
*/
public class Card {
/**
* The name of this card.
*/
private final String name;
/**
* Counts the number of instantiations of this class.
*/
private static int counter = 0;
/**
* The unique serial number of this card.
*/
private final int number;
/**
* Creates a new card with the specified name.
*
* @param name the name of this card
*/
public Card(String name) {
if (name == null)
throw new NullPointerException("name is null");
this.name = name;
this.number = ++counter;
}
/**
* Creates a new card for a student with the specified number.
*
* @param num the student's number
*/
public Card(int num) {
this("MatrNr. " + num);
}
/**
* Returns the name of this card.
*
* @return the name
*/
public String getName() {
return name;
}
/**
* Returns the serial number of this card.
*
* @return the serial number
*/
public int getNumber() {
return number;
}
/**
* Returns the number of instantiations of this class.
*
* @return the number of instantiations.
*/
public static int getCounter() {
return counter;
}
/**
* Returns a string representation of this card.
*/
@Override
public String toString() {
return "Card " + name + " (no " + number + ")";
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o instanceof Card) {
final Card that = (Card) o;
return that.canEqual(this) && this.name.equals(that.name);
}
return false;
}
public boolean canEqual(Object other) {
return other instanceof Card;
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch04.equality.card4;
public enum Color {
red, green, blue
}

View File

@@ -0,0 +1,32 @@
package oop.ch04.equality.card4;
public class ColoredCard extends Card {
public final Color color;
public ColoredCard(String key, Color color) {
super(key);
this.color = color;
}
@Override
public String toString() {
return color + " " + super.toString();
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o instanceof ColoredCard) {
final ColoredCard that = (ColoredCard) o;
return that.canEqual(this) &&
this.color == that.color &&
super.equals(that);
}
return false;
}
@Override
public boolean canEqual(Object other) {
return other instanceof ColoredCard;
}
}

View File

@@ -0,0 +1,29 @@
package oop.ch04.equality.card4;
import java.util.List;
import static oop.ch04.equality.card4.Color.green;
import static oop.ch04.equality.card4.Color.red;
public class Example {
public static void main(String[] args) {
final Card k1 = new Card("foo");
final Card k2 = new Card("foo");
final Card k3 = new Card("gnat");
final Card c1 = new ColoredCard("foo", green);
final Card c2 = new ColoredCard("foo", red);
final Card c3 = new ColoredCard("foo", red);
final Card c4 = new ColoredCard("gnat", red);
List<Card> cards = List.of(k1, k2, k3, c1, c2, c3, c4);
for (Card x1 : cards) {
System.out.println(x1);
for (Card x2 : cards)
if (x1.equals(x2))
System.out.println(" equal to " + x2);
else
System.out.println(" NOT equal to " + x2);
}
}
}

View File

@@ -0,0 +1,23 @@
package oop.ch04.equality.rational1;
import java.util.HashSet;
import java.util.Set;
public class Example {
public static void main(String[] args) {
Rational r1 = new Rational(1, 2);
Rational r2 = new Rational(2, 4);
System.out.println(r1 == r2);
System.out.println(r1.equals(r2));
Set<Rational> s1 = new HashSet<>();
s1.add(new Rational(1, 2));
s1.add(new Rational(1, 2));
System.out.println(s1);
Set<Rational> s2 = new HashSet<>();
s2.add(new Rational(1, 2));
s2.add(new Rational(1, 3));
System.out.println(s2.contains(new Rational(1, 3)));
}
}

View File

@@ -0,0 +1,117 @@
package oop.ch04.equality.rational1;
public class Rational {
private final int num;
private final int denom;
public Rational(int num, int denom) {
int gcd = gcDivider(Math.abs(num), Math.abs(denom));
if (denom < 0) {
this.num = -num / gcd;
this.denom = -denom / gcd;
}
else {
this.num = num / gcd;
this.denom = denom / gcd;
}
}
public Rational(int num) {
this(num, 1);
}
private int gcDivider(int x, int y) {
return x == 0 ? y : gcDivider(y % x, x);
}
public int getNum() {
return num;
}
public int getDenom() {
return denom;
}
public Rational add(Rational r) {
return new Rational(num * r.denom + denom * r.num, denom * r.denom);
}
public Rational add(int i) {
return this.add(new Rational(i));
}
public Rational sub(Rational r) {
return new Rational(num * r.denom - denom * r.num, denom * r.denom);
}
public Rational sub(int i) {
return this.sub(new Rational(i));
}
public Rational mult(Rational r) {
return new Rational(num * r.num, denom * r.denom);
}
public Rational mult(int i) {
return this.mult(new Rational(i));
}
public Rational div(Rational r) {
return new Rational(num * r.denom, denom * r.num);
}
public Rational div(int i) {
return this.div(new Rational(i));
}
public boolean lessThan(Rational r) {
return (this.sub(r).num < 0);
}
public boolean lessThan(int i) {
return (this.sub(i).num < 0);
}
public boolean greaterThan(Rational r) {
return (this.sub(r).num > 0);
}
public boolean greaterThan(int i) {
return (this.sub(i).num > 0);
}
public boolean lessThanOrEqual(Rational r) {
return (this.sub(r).num <= 0);
}
public boolean lessThanOrEqual(int i) {
return (this.sub(i).num <= 0);
}
public boolean greaterThanOrEqual(Rational r) {
return (this.sub(r).num <= 0);
}
public boolean greaterThanOrEqual(int i) {
return (this.sub(i).num <= 0);
}
@Override
public boolean equals(Object o) {
if (o == this) return true;
if (o instanceof Rational) {
final Rational that = (Rational) o;
return this.denom == that.denom && this.num == that.num;
}
return false;
}
public boolean equals(int i) {
return this.equals(new Rational(i));
}
@Override
public String toString() {
return denom == 1 ? "" + num : num + "/" + denom;
}
}

View File

@@ -0,0 +1,23 @@
package oop.ch04.equality.rational2;
import java.util.HashSet;
import java.util.Set;
public class Example {
public static void main(String[] args) {
Rational r1 = new Rational(1, 2);
Rational r2 = new Rational(2, 4);
System.out.println(r1 == r2);
System.out.println(r1.equals(r2));
Set<Rational> s1 = new HashSet<>();
s1.add(new Rational(1, 2));
s1.add(new Rational(1, 2));
System.out.println(s1);
Set<Rational> s2 = new HashSet<>();
s2.add(new Rational(1, 2));
s2.add(new Rational(1, 3));
System.out.println(s2.contains(new Rational(1, 3)));
}
}

View File

@@ -0,0 +1,122 @@
package oop.ch04.equality.rational2;
public class Rational {
private final int num;
private final int denom;
public Rational(int num, int denom) {
int gcd = gcDivider(Math.abs(num), Math.abs(denom));
if (denom < 0) {
this.num = -num / gcd;
this.denom = -denom / gcd;
}
else {
this.num = num / gcd;
this.denom = denom / gcd;
}
}
public Rational(int num) {
this(num, 1);
}
private int gcDivider(int x, int y) {
return x == 0 ? y : gcDivider(y % x, x);
}
public int getNum() {
return num;
}
public int getDenom() {
return denom;
}
public Rational add(Rational r) {
return new Rational(num * r.denom + denom * r.num, denom * r.denom);
}
public Rational add(int i) {
return this.add(new Rational(i));
}
public Rational sub(Rational r) {
return new Rational(num * r.denom - denom * r.num, denom * r.denom);
}
public Rational sub(int i) {
return this.sub(new Rational(i));
}
public Rational mult(Rational r) {
return new Rational(num * r.num, denom * r.denom);
}
public Rational mult(int i) {
return this.mult(new Rational(i));
}
public Rational div(Rational r) {
return new Rational(num * r.denom, denom * r.num);
}
public Rational div(int i) {
return this.div(new Rational(i));
}
public boolean lessThan(Rational r) {
return (this.sub(r).num < 0);
}
public boolean lessThan(int i) {
return (this.sub(i).num < 0);
}
public boolean greaterThan(Rational r) {
return (this.sub(r).num > 0);
}
public boolean greaterThan(int i) {
return (this.sub(i).num > 0);
}
public boolean lessThanOrEqual(Rational r) {
return (this.sub(r).num <= 0);
}
public boolean lessThanOrEqual(int i) {
return (this.sub(i).num <= 0);
}
public boolean greaterThanOrEqual(Rational r) {
return (this.sub(r).num <= 0);
}
public boolean greaterThanOrEqual(int i) {
return (this.sub(i).num <= 0);
}
@Override
public boolean equals(Object o) {
if (o == this) return true;
if (o instanceof Rational) {
final Rational that = (Rational) o;
return this.denom == that.denom && this.num == that.num;
}
return false;
}
@Override
public int hashCode() {
return num + denom;
}
public boolean equals(int i) {
return this.equals(new Rational(i));
}
@Override
public String toString() {
return denom == 1 ? "" + num : num + "/" + denom;
}
}

View File

@@ -0,0 +1,22 @@
package oop.ch05.generic.example;
import oop.ch03.vehicles.Auto;
public class AutoContainer {
private final double maxAchsLast;
private Auto contained;
public AutoContainer(double maxAchsLast) {
this.maxAchsLast = maxAchsLast;
}
public Auto getContained() {
return contained;
}
public void setContained(Auto auto) {
if (auto.getAchslast() > maxAchsLast)
throw new IllegalArgumentException("Too heavy");
this.contained = auto;
}
}

View File

@@ -0,0 +1,54 @@
package oop.ch05.generic.example;
import oop.ch03.vehicles.Amphibienfahrzeug;
import oop.ch03.vehicles.AmphibienfahrzeugImpl;
import oop.ch03.vehicles.Auto;
import oop.ch03.vehicles.AutoImpl;
public class Example {
public static void main(String[] args) {
plainTest();
genericTest();
}
public static void plainTest() {
final Amphibienfahrzeug alligator = new AmphibienfahrzeugImpl(750, 8000);
final Auto golf = new AutoImpl(500);
final AutoContainer c = new AutoContainer(1000);
c.setContained(alligator);
System.out.println("Tiefgang: " + getTiefgang(c));
c.setContained(golf);
System.out.println("Tiefgang: " + getTiefgang(c));
}
public static void genericTest() {
final Amphibienfahrzeug alligator = new AmphibienfahrzeugImpl(750, 8000);
final Auto golf = new AutoImpl(500);
final GenericContainer<Amphibienfahrzeug> c1 = new GenericContainer<>(1000);
c1.setContained(alligator);
System.out.println("Tiefgang: " + getTiefgang(c1));
// incompatible types: oop.ch04.vehicles.Auto cannot be converted to oop.ch04.vehicles.Amphibienfahrzeug
// c1.setContained(golf);
System.out.println("Tiefgang: " + getTiefgang(c1));
final GenericContainer<Auto> c2 = new GenericContainer<>(1000);
c2.setContained(golf);
// no suitable method found for getTiefgang(oop.ch05.generic.example.GenericContainer<oop.ch04.vehicles.Auto>)
// System.out.println("Tiefgang: " + getTiefgang(c2));
}
public static double getTiefgang(AutoContainer container) {
final Amphibienfahrzeug contained = (Amphibienfahrzeug) container.getContained();
return contained.getTiefgang();
}
public static double getTiefgang(GenericContainer<Amphibienfahrzeug> container) {
return container.getContained().getTiefgang();
}
}

View File

@@ -0,0 +1,22 @@
package oop.ch05.generic.example;
import oop.ch03.vehicles.Auto;
public class GenericContainer<A extends Auto> {
private final double maxAchsLast;
private A contained;
public GenericContainer(double maxAchsLast) {
this.maxAchsLast = maxAchsLast;
}
public A getContained() {
return contained;
}
public void setContained(A auto) {
if (auto.getAchslast() > maxAchsLast)
throw new IllegalArgumentException("Too heavy");
this.contained = auto;
}
}

View File

@@ -0,0 +1,34 @@
package oop.ch05.generic.mensa;
import oop.ch05.generic.secured.AuthorizationException;
import oop.ch05.generic.secured.SecuredContent;
import oop.ch05.generic.secured.SecurityClient;
public class AccountCard extends MensaCard {
private final SecuredContent<String> account;
public AccountCard(String key, String account, int password) {
super(key, Color.white);
this.account = new SecuredContent<>(password, account);
}
public String getAccount() {
return account.getContent();
}
public void setAccount(SecurityClient client, String account) throws AuthorizationException {
if (account == null || account.trim().length() == 0)
throw new IllegalArgumentException("Invalid account " + account);
this.account.setContent(client, account);
}
@Override
public String toString() {
return super.toString() + " for account " + account.getContent();
}
@Override
public void pass(CashPoint cashPoint) {
cashPoint.charge(this);
}
}

View File

@@ -0,0 +1,43 @@
package oop.ch05.generic.mensa;
import oop.ch05.generic.secured.AuthorizationException;
import oop.ch05.generic.secured.SecuredContent;
public class CashCard extends MensaCard {
private final SecuredContent<Integer> balance;
public CashCard(String key, Color color, int password) {
super(key, color);
balance = new SecuredContent<>(password, 0);
if (color != Color.blue && color != Color.green)
throw new IllegalArgumentException("Invalid CashCard color " + color);
}
public int getBalance() {
return balance.getContent();
}
void deposit(VendingMachine client, int cents)
throws AuthorizationException {
if (cents <= 0)
throw new IllegalArgumentException("Non-positive deposit");
final int newBalance = getBalance() + cents;
balance.setContent(client, newBalance);
}
void charge(CashPoint client, int cents) throws AuthorizationException {
if (cents < 0)
throw new IllegalArgumentException("Negative charge");
balance.setContent(client, getBalance() - cents);
}
@Override
public String toString() {
return super.toString() + " with " + balance.getContent() + " cents";
}
@Override
public void pass(CashPoint cashPoint) throws AuthorizationException, RejectedException {
cashPoint.charge(this);
}
}

View File

@@ -0,0 +1,64 @@
package oop.ch05.generic.mensa;
import oop.ch05.generic.secured.AuthorizationException;
import oop.ch05.generic.secured.SecurityClient;
public class CashPoint implements SecurityClient {
private final int password;
public final String name;
private int counter;
private int cents;
public CashPoint(String name, int password) {
this.name = name;
this.password = password;
this.counter = 0;
this.cents = 0;
}
@Override
public int challengeResponse(int challenge) {
return challenge ^ password;
}
@Override
public String toString() {
return "Cash point " + name + " (" + getCounter() + " meals, " + getCents() + " cents charged)";
}
public int getCounter() {
return counter;
}
public int getCents() {
return cents;
}
private int getPrice(Color color) {
return switch (color) {
case green -> 267;
case blue -> 357;
case white -> 495;
default -> 0;
};
}
void count(MensaCard card) {
counter++;
}
void charge(CashCard cashCard) throws AuthorizationException, RejectedException {
final int price = getPrice(cashCard.color);
if (cashCard.getBalance() < price)
throw new RejectedException("insufficient payment");
cashCard.charge(this, price);
count(cashCard);
cents += price;
}
void charge(AccountCard accountCard) {
final int price = getPrice(accountCard.color);
System.out.println("Charging " + price + " cents on account " + accountCard.getAccount());
cents += price;
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch05.generic.mensa;
public enum Color {
green, red, blue, white, gray
}

View File

@@ -0,0 +1,15 @@
package oop.ch05.generic.mensa;
public class CountCard extends MensaCard {
public CountCard(String key, Color color) {
super(key, color);
if (color != Color.red && color != Color.gray)
throw new IllegalArgumentException("Invalid CountCard color " + color);
}
@Override
public void pass(CashPoint cashPoint) {
cashPoint.count(this);
}
}

View File

@@ -0,0 +1,20 @@
package oop.ch05.generic.mensa;
import oop.ch02.cards.Card;
import oop.ch05.generic.secured.AuthorizationException;
public abstract class MensaCard extends Card {
public final Color color;
protected MensaCard(String name, Color color) {
super(name);
this.color = color;
}
@Override
public String toString() {
return color + " card " + getNumber() + " (" + getName() + ")";
}
public abstract void pass(CashPoint cashPoint) throws RejectedException, AuthorizationException;
}

View File

@@ -0,0 +1,68 @@
package oop.ch05.generic.mensa;
import oop.ch05.generic.secured.AuthorizationException;
public class MensaExample {
public static void main(String[] args) {
VendingMachine vm1 = new VendingMachine("left", 4711);
VendingMachine vm2 = new VendingMachine("right", 4711);
VendingMachine tumVM = new VendingMachine("TUM Mensa", 3141);
CashPoint unibwMensa = new CashPoint("UniBw Mensa", 4711);
AccountCard conf = new AccountCard("conference", "33-1298", 42);
MensaCard frankSmith = new CountCard("Frank Smith", Color.gray);
CashCard hansMueller = new CashCard("Hans Müller", Color.green, 4711);
CashCard peterSchmidt = new CashCard("Peter Schmidt", Color.green, 4711);
CashCard thomasMayer = new CashCard("Thomas Mayer", Color.blue, 4711);
deposit(vm1, hansMueller, 10);
deposit(vm1, peterSchmidt, 5);
deposit(vm2, thomasMayer, 2);
deposit(tumVM, hansMueller, 10);
System.out.println(vm1);
System.out.println(vm2);
System.out.println(tumVM);
System.out.println(hansMueller);
System.out.println(peterSchmidt);
System.out.println(thomasMayer);
System.out.println();
pass(hansMueller, unibwMensa);
System.out.println(hansMueller);
System.out.println(unibwMensa);
pass(frankSmith, unibwMensa);
pass(conf, unibwMensa);
pass(thomasMayer, unibwMensa);
pass(hansMueller, unibwMensa);
pass(hansMueller, unibwMensa);
pass(hansMueller, unibwMensa);
System.out.println(unibwMensa);
System.out.println(hansMueller);
System.out.println(peterSchmidt);
System.out.println(thomasMayer);
}
private static void pass(MensaCard mensaCard, CashPoint cashPoint) {
try {
mensaCard.pass(cashPoint);
}
catch (RejectedException e) {
System.out.println("rejected: " + e.getMessage());
}
catch (AuthorizationException e) {
System.out.println("authrozation failed: " + e.getMessage());
}
}
private static void deposit(VendingMachine vm, CashCard cashCard, int euros) {
try {
vm.deposit(cashCard, euros);
}
catch (AuthorizationException e) {
System.out.println("authorization failed: " + e.getMessage());
}
}
}

View File

@@ -0,0 +1,7 @@
package oop.ch05.generic.mensa;
public class RejectedException extends Exception {
public RejectedException(String message) {
super(message);
}
}

View File

@@ -0,0 +1,37 @@
package oop.ch05.generic.mensa;
import oop.ch05.generic.secured.AuthorizationException;
import oop.ch05.generic.secured.SecurityClient;
public class VendingMachine implements SecurityClient {
private final int password;
public final String name;
private int euros;
public VendingMachine(String name, int password) {
this.name = name;
this.password = password;
this.euros = 0;
}
@Override
public int challengeResponse(int challenge) {
return challenge ^ password;
}
@Override
public String toString() {
return "Vending machine " + name + " (contains EUR " + euros + ")";
}
public int getEuros() {
return euros;
}
public void deposit(CashCard card, int euros) throws AuthorizationException {
if (euros <= 0)
throw new IllegalArgumentException("Non-positive deposit");
card.deposit(this, euros * 100);
this.euros += euros;
}
}

View File

@@ -0,0 +1,20 @@
package oop.ch05.generic.secured;
/**
* This class represents exceptions that are thrown whenever an authorization
* fails.
*
* @author Mark Minas
*/
public class AuthorizationException extends Exception {
/**
* Constructs a new authorization exception with the specified detail message
* and cause.
*
* @param message the detail message (which is saved for later retrieval by the
* {@link #getMessage()} method).
*/
public AuthorizationException(String message) {
super(message);
}
}

View File

@@ -0,0 +1,80 @@
package oop.ch05.generic.secured;
import java.util.Random;
/**
* Represents containers for some content that is secured against modifications
* by a challenge-response approach. The content may be read at any time, but
* only authorized clients are allowed to modify the contents.
*
* @param <E> the type of the actual secured content
* @author Mark Minas
*/
public class SecuredContent<E> {
/**
* The actual, secured content
*/
private E content;
/**
* A random number generator used for generating challenges.
*/
private final Random random = new Random();
/**
* The password used for encryption.
*/
private final int password;
/**
* Creates a new container containing the specified contents.
*
* @param password this password is used for computing the expected response for a
* challenge.
* @param content the contained content
*/
public SecuredContent(int password, E content) {
this.password = password;
this.content = content;
}
/**
* Returns the contained contents. There is no authorization necessary for
* reading the contents.
*/
public E getContent() {
return content;
}
/**
* Sets the new contained contents. Only authorized clients are allowed to do
* so.
*
* @param client The accessing client. Authorization is checked prior to really
* modifying he contained content.
* @param content The new contained contents
* @throws AuthorizationException if the specified client cannot authorize himself
*/
public void setContent(SecurityClient client, E content)
throws AuthorizationException {
final int challenge = nextChallenge();
if (client.challengeResponse(challenge) != requiredResponse(challenge))
throw new AuthorizationException(client
+ " is not authorized to access contents.");
this.content = content;
}
/**
* Computes the next random challenge.
*/
private int nextChallenge() {
return random.nextInt();
}
/**
* Returns the expected response for the specified challenge.
*
* @param challenge an arbitrary integer used as a challenge
*/
private int requiredResponse(int challenge) {
return challenge ^ password;
}
}

View File

@@ -0,0 +1,18 @@
package oop.ch05.generic.secured;
/**
* This interface must be implemented by any client that is going to be
* authorized by a challenge-response approach.
*
* @author Mark Minas
*/
public interface SecurityClient {
/**
* Returns the response for the specified challenge. Authorization succeeds
* if this response is the same as the one expected by the server.
*
* @param challenge the integer number for which the correct response has to be
* computed.
*/
int challengeResponse(int challenge);
}

View File

@@ -0,0 +1,34 @@
package oop.ch05.mensa;
import oop.ch05.secured.AuthorizationException;
import oop.ch05.secured.SecuredContent;
import oop.ch05.secured.SecurityClient;
public class AccountCard extends MensaCard {
private final SecuredContent account;
public AccountCard(String key, String account, int password) {
super(key, Color.white);
this.account = new SecuredContent(password, account);
}
public String getAccount() {
return (String) account.getContent();
}
public void setAccount(SecurityClient client, String account) throws AuthorizationException {
if (account == null || account.trim().length() == 0)
throw new IllegalArgumentException("Invalid account " + account);
this.account.setContent(client, account);
}
@Override
public String toString() {
return super.toString() + " for account " + account.getContent();
}
@Override
public void pass(CashPoint cashPoint) {
cashPoint.charge(this);
}
}

View File

@@ -0,0 +1,43 @@
package oop.ch05.mensa;
import oop.ch05.secured.AuthorizationException;
import oop.ch05.secured.SecuredContent;
public class CashCard extends MensaCard {
private final SecuredContent balance;
public CashCard(String key, Color color, int password) {
super(key, color);
balance = new SecuredContent(password, 0);
if (color != Color.blue && color != Color.green)
throw new IllegalArgumentException("Invalid CashCard color " + color);
}
public int getBalance() {
return (Integer) balance.getContent();
}
void deposit(VendingMachine client, int cents)
throws AuthorizationException {
if (cents <= 0)
throw new IllegalArgumentException("Non-positive deposit");
final int newBalance = getBalance() + cents;
balance.setContent(client, newBalance);
}
void charge(CashPoint client, int cents) throws AuthorizationException {
if (cents < 0)
throw new IllegalArgumentException("Negative charge");
balance.setContent(client, getBalance() - cents);
}
@Override
public String toString() {
return super.toString() + " with " + balance.getContent() + " cents";
}
@Override
public void pass(CashPoint cashPoint) throws AuthorizationException, RejectedException {
cashPoint.charge(this);
}
}

View File

@@ -0,0 +1,64 @@
package oop.ch05.mensa;
import oop.ch05.secured.AuthorizationException;
import oop.ch05.secured.SecurityClient;
public class CashPoint implements SecurityClient {
private final int password;
public final String name;
private int counter;
private int cents;
public CashPoint(String name, int password) {
this.name = name;
this.password = password;
this.counter = 0;
this.cents = 0;
}
@Override
public int challengeResponse(int challenge) {
return challenge ^ password;
}
@Override
public String toString() {
return "Cash point " + name + " (" + getCounter() + " meals, " + getCents() + " cents charged)";
}
public int getCounter() {
return counter;
}
public int getCents() {
return cents;
}
private int getPrice(Color color) {
return switch (color) {
case green -> 267;
case blue -> 357;
case white -> 495;
default -> 0;
};
}
void count(MensaCard card) {
counter++;
}
void charge(CashCard cashCard) throws AuthorizationException, RejectedException {
final int price = getPrice(cashCard.color);
if (cashCard.getBalance() < price)
throw new RejectedException("insufficient payment");
cashCard.charge(this, price);
count(cashCard);
cents += price;
}
void charge(AccountCard accountCard) {
final int price = getPrice(accountCard.color);
System.out.println("Charging " + price + " cents on account " + accountCard.getAccount());
cents += price;
}
}

View File

@@ -0,0 +1,5 @@
package oop.ch05.mensa;
public enum Color {
green, red, blue, white, gray
}

View File

@@ -0,0 +1,15 @@
package oop.ch05.mensa;
public class CountCard extends MensaCard {
public CountCard(String key, Color color) {
super(key, color);
if (color != Color.red && color != Color.gray)
throw new IllegalArgumentException("Invalid CountCard color " + color);
}
@Override
public void pass(CashPoint cashPoint) {
cashPoint.count(this);
}
}

View File

@@ -0,0 +1,20 @@
package oop.ch05.mensa;
import oop.ch02.cards.Card;
import oop.ch05.secured.AuthorizationException;
public abstract class MensaCard extends Card {
public final Color color;
protected MensaCard(String name, Color color) {
super(name);
this.color = color;
}
@Override
public String toString() {
return color + " card " + getNumber() + " (" + getName() + ")";
}
public abstract void pass(CashPoint cashPoint) throws RejectedException, AuthorizationException;
}

View File

@@ -0,0 +1,68 @@
package oop.ch05.mensa;
import oop.ch05.secured.AuthorizationException;
public class MensaExample {
public static void main(String[] args) {
VendingMachine vm1 = new VendingMachine("left", 4711);
VendingMachine vm2 = new VendingMachine("right", 4711);
VendingMachine tumVM = new VendingMachine("TUM Mensa", 3141);
CashPoint unibwMensa = new CashPoint("UniBw Mensa", 4711);
AccountCard conf = new AccountCard("conference", "33-1298", 42);
MensaCard frankSmith = new CountCard("Frank Smith", Color.gray);
CashCard hansMueller = new CashCard("Hans Müller", Color.green, 4711);
CashCard peterSchmidt = new CashCard("Peter Schmidt", Color.green, 4711);
CashCard thomasMayer = new CashCard("Thomas Mayer", Color.blue, 4711);
deposit(vm1, hansMueller, 10);
deposit(vm1, peterSchmidt, 5);
deposit(vm2, thomasMayer, 2);
deposit(tumVM, hansMueller, 10);
System.out.println(vm1);
System.out.println(vm2);
System.out.println(tumVM);
System.out.println(hansMueller);
System.out.println(peterSchmidt);
System.out.println(thomasMayer);
System.out.println();
pass(hansMueller, unibwMensa);
System.out.println(hansMueller);
System.out.println(unibwMensa);
pass(frankSmith, unibwMensa);
pass(conf, unibwMensa);
pass(thomasMayer, unibwMensa);
pass(hansMueller, unibwMensa);
pass(hansMueller, unibwMensa);
pass(hansMueller, unibwMensa);
System.out.println(unibwMensa);
System.out.println(hansMueller);
System.out.println(peterSchmidt);
System.out.println(thomasMayer);
}
private static void pass(MensaCard mensaCard, CashPoint cashPoint) {
try {
mensaCard.pass(cashPoint);
}
catch (RejectedException e) {
System.out.println("rejected: " + e.getMessage());
}
catch (AuthorizationException e) {
System.out.println("authrozation failed: " + e.getMessage());
}
}
private static void deposit(VendingMachine vm, CashCard cashCard, int euros) {
try {
vm.deposit(cashCard, euros);
}
catch (AuthorizationException e) {
System.out.println("authorization failed: " + e.getMessage());
}
}
}

View File

@@ -0,0 +1,7 @@
package oop.ch05.mensa;
public class RejectedException extends Exception {
public RejectedException(String message) {
super(message);
}
}

View File

@@ -0,0 +1,37 @@
package oop.ch05.mensa;
import oop.ch05.secured.AuthorizationException;
import oop.ch05.secured.SecurityClient;
public class VendingMachine implements SecurityClient {
private final int password;
public final String name;
private int euros;
public VendingMachine(String name, int password) {
this.name = name;
this.password = password;
this.euros = 0;
}
@Override
public int challengeResponse(int challenge) {
return challenge ^ password;
}
@Override
public String toString() {
return "Vending machine " + name + " (contains EUR " + euros + ")";
}
public int getEuros() {
return euros;
}
public void deposit(CashCard card, int euros) throws AuthorizationException {
if (euros <= 0)
throw new IllegalArgumentException("Non-positive deposit");
card.deposit(this, euros * 100);
this.euros += euros;
}
}

View File

@@ -0,0 +1,20 @@
package oop.ch05.secured;
/**
* This class represents exceptions that are thrown whenever an authorization
* fails.
*
* @author Mark Minas
*/
public class AuthorizationException extends Exception {
/**
* Constructs a new authorization exception with the specified detail message
* and cause.
*
* @param message the detail message (which is saved for later retrieval by the
* {@link #getMessage()} method).
*/
public AuthorizationException(String message) {
super(message);
}
}

View File

@@ -0,0 +1,79 @@
package oop.ch05.secured;
import java.util.Random;
/**
* Represents containers for some content that is secured against modifications
* by a challenge-response approach. The content may be read at any time, but
* only authorized clients are allowed to modify the contents.
*
* @author Mark Minas
*/
public class SecuredContent {
/**
* The actual, secured content
*/
private Object content;
/**
* A random number generator used for generating challenges.
*/
private final Random random = new Random();
/**
* The password used for encryption.
*/
private final int password;
/**
* Creates a new container containing the specified contents.
*
* @param password this password is used for computing the expected response for a
* challenge.
* @param content the contained content
*/
public SecuredContent(int password, Object content) {
this.password = password;
this.content = content;
}
/**
* Returns the contained contents. There is no authorization necessary for
* reading the contents.
*/
public Object getContent() {
return content;
}
/**
* Sets the new contained contents. Only authorized clients are allowed to do
* so.
*
* @param client The accessing client. Authorization is checked prior to really
* modifying he contained content.
* @param content The new contained contents
* @throws AuthorizationException if the specified client cannot authorize himself
*/
public void setContent(SecurityClient client, Object content)
throws AuthorizationException {
final int challenge = nextChallenge();
if (client.challengeResponse(challenge) != requiredResponse(challenge))
throw new AuthorizationException(client
+ " is not authorized to access contents.");
this.content = content;
}
/**
* Computes the next random challenge.
*/
private int nextChallenge() {
return random.nextInt();
}
/**
* Returns the expected response for the specified challenge.
*
* @param challenge an arbitrary integer used as a challenge
*/
private int requiredResponse(int challenge) {
return challenge ^ password;
}
}

View File

@@ -0,0 +1,18 @@
package oop.ch05.secured;
/**
* This interface must be implemented by any client that is going to be
* authorized by a challenge-response approach.
*
* @author Mark Minas
*/
public interface SecurityClient {
/**
* Returns the response for the specified challenge. Authorization succeeds
* if this response is the same as the one expected by the server.
*
* @param challenge the integer number for which the correct response has to be
* computed.
*/
int challengeResponse(int challenge);
}

View File

@@ -0,0 +1,113 @@
package oop.ch06.calc;
import oop.ch06.observer.ObserverSupport;
public class AdHocCalculator extends ObserverSupport {
private double value;
private double opnd1;
private BinaryOp lastOp;
private double factor;
private boolean startedNumTyping;
private boolean hasSecondOpnd;
public double getValue() {return value;}
private void setValue(double n) {
value = n;
notifyObservers();
}
public void digit(int d) {
if (!Double.isNaN(value)) {
if (!startedNumTyping) {
startedNumTyping = true;
setValue(d);
factor = 1.;
}
else if (factor < 1.) {
setValue(value + factor * d);
factor *= 0.1;
}
else
setValue(10. * value + d);
if (lastOp != null)
hasSecondOpnd = true;
}
}
public void dot() {
if (!Double.isNaN(value)) {
if (!startedNumTyping) {
startedNumTyping = true;
setValue(0);
factor = 0.1;
}
else if (factor > 0.1)
factor = 0.1;
if (lastOp != null)
hasSecondOpnd = true;
}
}
public void unOp(UnaryOp op) {
try {
if (!Double.isNaN(value)) {
startedNumTyping = false;
setValue(op.eval(value));
if (lastOp != null)
hasSecondOpnd = true;
}
}
catch (CalculatorError ex) {
setValue(Double.NaN);
}
}
public void binOp(BinaryOp op) {
try {
if (!Double.isNaN(value)) {
startedNumTyping = false;
if (lastOp == null) {
opnd1 = value;
hasSecondOpnd = false;
}
else if (hasSecondOpnd) {
setValue(lastOp.eval(opnd1, value));
opnd1 = value;
}
lastOp = op;
}
}
catch (CalculatorError ex) {
setValue(Double.NaN);
}
}
public void eval() {
try {
if (!Double.isNaN(value) && lastOp != null) {
startedNumTyping = false;
setValue(lastOp.eval(opnd1, value));
lastOp = null;
}
}
catch (CalculatorError ex) {
setValue(Double.NaN);
}
}
public void clear() {
if (!Double.isNaN(value)) {
setValue(0);
startedNumTyping = false;
hasSecondOpnd = false;
}
}
public void allClear() {
setValue(0);
startedNumTyping = false;
hasSecondOpnd = false;
lastOp = null;
}
}

View File

@@ -0,0 +1,9 @@
package oop.ch06.calc;
public abstract class BinaryOp extends Op {
protected BinaryOp(String name) {
super(name);
}
public abstract double eval(double opnd1, double opnd2);
}

View File

@@ -0,0 +1,7 @@
package oop.ch06.calc;
public class CalculatorError extends RuntimeException {
public CalculatorError(String message) {
super(message);
}
}

Some files were not shown because too many files have changed in this diff Show More