Skip to content

Commit

Permalink
docs: update twin
Browse files Browse the repository at this point in the history
  • Loading branch information
iluwatar committed May 27, 2024
1 parent 4b5f34e commit d26454a
Showing 1 changed file with 69 additions and 8 deletions.
77 changes: 69 additions & 8 deletions twin/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,9 @@ public class BallItem extends GameItem {
}
}
}
```

```java
@Slf4j
public class BallThread extends Thread {
@Setter
Expand Down Expand Up @@ -117,25 +119,85 @@ public class BallThread extends Thread {
To use these classes together:

```java
var ballItem = new BallItem();
var ballThread = new BallThread();
public class App {

public static void main(String[] args) throws Exception {

var ballItem = new BallItem();
var ballThread = new BallThread();

ballItem.setTwin(ballThread);
ballThread.setTwin(ballItem);

ballThread.start();

ballItem.setTwin(ballThread);
ballThread.setTwin(ballItem);
waiting();

ballItem.click();

waiting();

ballItem.click();

waiting();

// exit
ballThread.stopMe();
}

private static void waiting() throws Exception {
Thread.sleep(750);
}
}
```

This setup allows `BallItem` and `BallThread` to act together as a single cohesive unit in the game, leveraging the capabilities of both `GameItem` and `Thread` without multiple inheritance.
Let's break down what happens in `App`.

## Class diagram
1. An instance of `BallItem` and `BallThread` are created.
2. The `BallItem` and `BallThread` instances are set as twins of each other. This means that each instance has a reference to the other.
3. The `BallThread` is started. This begins the execution of the `run` method in the `BallThread` class, which continuously calls the `draw` and `move` methods of the `BallItem` (its twin) as long as the `BallThread` is not suspended.
4. The program waits for 750 milliseconds. This is done to allow the `BallThread` to execute its `run` method a few times.
5. The `click` method of the `BallItem` is called. This toggles the `isSuspended` state of the `BallItem` and its twin `BallThread`. If the `BallThread` was running, it gets suspended. If it was suspended, it resumes running.
6. Steps 4 and 5 are repeated twice. This means the `BallThread` is suspended and resumed once.
7. Finally, the `stopMe` method of the `BallThread` is called to stop its execution.

![Twin](./etc/twin.png "Twin")
Console output:

```
14:29:33.778 [Thread-0] INFO com.iluwatar.twin.GameItem -- draw
14:29:33.780 [Thread-0] INFO com.iluwatar.twin.BallItem -- doDraw
14:29:33.780 [Thread-0] INFO com.iluwatar.twin.BallItem -- move
14:29:34.035 [Thread-0] INFO com.iluwatar.twin.GameItem -- draw
14:29:34.035 [Thread-0] INFO com.iluwatar.twin.BallItem -- doDraw
14:29:34.035 [Thread-0] INFO com.iluwatar.twin.BallItem -- move
14:29:34.291 [Thread-0] INFO com.iluwatar.twin.GameItem -- draw
14:29:34.291 [Thread-0] INFO com.iluwatar.twin.BallItem -- doDraw
14:29:34.291 [Thread-0] INFO com.iluwatar.twin.BallItem -- move
14:29:34.533 [main] INFO com.iluwatar.twin.BallThread -- Begin to suspend BallThread
14:29:35.285 [main] INFO com.iluwatar.twin.BallThread -- Begin to resume BallThread
14:29:35.308 [Thread-0] INFO com.iluwatar.twin.GameItem -- draw
14:29:35.308 [Thread-0] INFO com.iluwatar.twin.BallItem -- doDraw
14:29:35.308 [Thread-0] INFO com.iluwatar.twin.BallItem -- move
14:29:35.564 [Thread-0] INFO com.iluwatar.twin.GameItem -- draw
14:29:35.564 [Thread-0] INFO com.iluwatar.twin.BallItem -- doDraw
14:29:35.565 [Thread-0] INFO com.iluwatar.twin.BallItem -- move
14:29:35.817 [Thread-0] INFO com.iluwatar.twin.GameItem -- draw
14:29:35.817 [Thread-0] INFO com.iluwatar.twin.BallItem -- doDraw
14:29:35.817 [Thread-0] INFO com.iluwatar.twin.BallItem -- move
```

This setup allows `BallItem` and `BallThread` to act together as a single cohesive unit in the game, leveraging the capabilities of both `GameItem` and `Thread` without multiple inheritance.

## Applicability

* Use when you need to decouple classes that share common functionality but cannot inherit from a common base class due to various reasons such as the use of different frameworks or languages.
* Useful in performance-critical applications where inheritance might introduce unnecessary overhead.
* Applicable in systems requiring resilience through the ability to replace or update one of the twins without affecting the other.

## Tutorials

* [Twin – A Design Pattern for Modeling Multiple Inheritance (Hanspeter Mössenböck)](http://www.ssw.uni-linz.ac.at/Research/Papers/Moe99/Paper.pdf)

## Known Uses

* User interfaces where different frameworks are used for rendering and logic.
Expand Down Expand Up @@ -165,4 +227,3 @@ Trade-offs:
* [Design Patterns: Elements of Reusable Object-Oriented Software](https://amzn.to/3w0pvKI)
* [Java Design Patterns: A Hands-On Experience with Real-World Examples](https://amzn.to/3yhh525)
* [Patterns of Enterprise Application Architecture](https://amzn.to/3WfKBPR)
* [Twin – A Design Pattern for Modeling Multiple Inheritance - Hanspeter Mössenböck](http://www.ssw.uni-linz.ac.at/Research/Papers/Moe99/Paper.pdf)

0 comments on commit d26454a

Please sign in to comment.