LeetCode Question · Feb 2024 · San Francisco

SDE3 | Machine Coding round | Kotak Bank | LLD | Data base design

7 upvotes 1,521 views 8 replies

Question Details

Below problem statement was given to me and expectation was to come up with a proper working code for it. BattleShip Game Design and implement a battleship game to be played between...

Full Details

Below problem statement was given to me and expectation was to come up with a proper working code for it.
BattleShip Game
Design and implement a battleship game to be played between two players until one comes out
as the winner.

Requirements:
\u25CF The game will be played in a square area of the sea with NxN grids which will be called
a battlefield. \u201CN\u201D should be taken as input in your code.
\u25CF The battlefield will be divided in half between both the players. So in a NxN battlefield,
NxN/2 grids will belong to PlayerA and the other NxN/2 grids will belong to playerB
\u25CF The size and location of each ship will be taken as input. Each ship will be assumed to
be of Square shape. Both the players should be assigned equal fleet.
\u25CF The location of each ship in the NxN grids has to be taken as input (X, Y). X and Y
should be integers. For eg. if a ship \u201CSH1\u201D is at (2, 2) and has the size of 4, its corners
will be at (0, 0), (0, 4), (4, 0) and (4,4)
\u25CF Ships will remain stationary. No two ships should overlap with each other. However they
can touch boundaries with each other.
\u25CF Each player will fire one missile towards the enemy field during his turn using the
\u201Crandom coordinate fire\u201D strategy, which means the missile will hit at a random
coordinate of the opponent\u2019s field. It might hit or miss the opponent ship. In either case
the turn is then transferred to the other player.
\u25CB In case of a hit, the opponent\u2019s ship is destroyed.
\u25CB In case of a miss, nothing happens.
\u25CF No two missiles should ever be fired at the same coordinates throughout the course
of the game.
\u25CF When all the ships of a particular player has been destroyed, he loses the game.
The following APIs have to be implemented:
Mandatory:
\u25CF initGame(N)

This will initialize the game with a battlefield of size NxN. Where the left half of
N/2xN will be assigned to PlayerA and the right half will be assigned to PlayerB
\u25CF addShip(id, size, x position PlayerA, y position PlayerA, x position PlayerB, y position
PlayerB)
This will add a ship of given size at the given coordinates in both the player\u2019s
fleet.
\u25CF startGame()

This will begin the game, where PlayerA will always take the first turn. The output
of each step should be printed clearly in the console.
For eg.
PlayerA\u2019s turn: Missile fired at (2, 4). \u201CHit\u201D. PlayerB\u2019s ship with id \u201CSH1\u201D
destroyed.
PlayerB\u2019s turn: Missile fired at (6, 1). \u201CMiss\u201D

Optional
\u25CF viewBattleField()

This will display the battlefield as a NxN grid and all the ships along with the grids
occupied by each ship. PlayerA\u2019s ship with id SH1 will be marked as A-SH1, with
id SH2 as A-SH2 and so on. Whereas PlayerB\u2019s ships will be marked as B-SH1,
B-SH2 and so on.

Note: It should mark all the grids occupied by a ship and not just the center
coordinate.

Here is Java code for above problem. And I was asked to come up with schema and data base design as well.

import java.util.*;

class Ship {
 private String name;
 private int size;
 private int x, y;
 private Set<String> coordinates;

 public Ship(String name, int size, int x, int y) {
 this.name = name;
 this.size = size;
 this.x = x;
 this.y = y;
 this.coordinates = new HashSet<>();
 for (int i = 0; i < size; i++) {
 for (int j = 0; j < size; j++) {
 coordinates.add((x + i) + "," + (y + j));
 }
 }
 }

 public Set<String> getCoordinates() {

**return** coordinates;
 }

 public String getName() {

**return** name;
 }
}

class Player {
 private String name;
 private List<Ship> ships;

 public Player(String name) {
 this.name = name;
 this.ships = new ArrayList<>();
 }

 public void addShip(Ship ship) {
 ships.add(ship);
 }

 public String getName() {

**return** name;
 }

 public List<Ship> getShips() {

**return** ships;
 }
}

class BattleShip {
 private int N;
 private char[][] battleField;
 private Player playerA;
 private Player playerB;
 private boolean gameStarted;

 public BattleShip() {
 this.gameStarted = false;
 }

 public void initGame(int N) {
 this.N = N;
 this.battleField = new char[N][N];
 for (char[] row : battleField) {
 Arrays.fill(row, \'.\');
 }
 int half = N / 2;
 playerA = new Player("Player A");
 playerB = new Player("Player B");
 gameStarted = false;
 }

 public Player getPlayerA() {

**return** playerA;
 }

 public Player getPlayerB() {

**return** playerB;
 }

 public void addShip(String id, int size, int xa, int ya, int xb, int yb) {
 if (gameStarted) {
 System.out.println("Game already started");
 return;
 }

 Ship shipA = new Ship(id, size, xa, ya);
 Ship shipB = new Ship(id, size, xb, yb);

 playerA.addShip(shipA);
 playerB.addShip(shipB);

 for (String coord : shipA.getCoordinates()) {
 String[] parts = coord.split(",");
 int x = Integer.parseInt(parts[0]);
 int y = Integer.parseInt(parts[1]);
 battleField[x][y] = \'A\';
 }

 for (String coord : shipB.getCoordinates()) {
 String[] parts = coord.split(",");
 int x = Integer.parseInt(parts[0]);
 int y = Integer.parseInt(parts[1]);
 battleField[x][y] = \'B\';
 }
 }

 public void startGame() {
 if (!gameStarted) {
 gameStarted = true;
 System.out.println("Game started!");
 } else {
 System.out.println("Game already started!");
 }
 }

 public void fireMissile(Player attacker, Player opponent) {
 if (!gameStarted) {
 System.out.println("Game has not started yet.");
 return;
 }

 Random rand = new Random();
 int x = rand.nextInt(N);
 int y = rand.nextInt(N);

 System.out.print(attacker.getName() + " fires missile at (" + x + "," + y + "). ");

 boolean hit = false;
 for (Ship ship : opponent.getShips()) {
 for (String coord : ship.getCoordinates()) {
 String[] parts = coord.split(",");
 int shipX = Integer.parseInt(parts[0]);
 int shipY = Integer.parseInt(parts[1]);
 if (shipX == x && shipY == y) {
 hit = true;
 System.out.println("Hit! " + opponent.getName() + "\'s ship with id " + ship.getName() + " destroyed.");
 break;
 }
 }
 if (hit) {
 break;
 }
 }

 if (!hit) {
 System.out.println("Miss!");
 }
 }

 public void viewBattleField() {
 System.out.println("BattleField :");
 for (int i = 0; i < N; i++) {
 for (int j = 0; j < N; j++) {
 System.out.print(battleField[i][j] + " ");
 }
 System.out.println();
 }
 }
}

public class Main {
 public static void main(String[] args) {
 BattleShip game = new BattleShip();
 game.initGame(10);

 game.addShip("SH1", 2, 1, 1, 4, 4);
 game.addShip("SH2", 3, 3, 3, 7, 7);

 game.startGame();

 Player playerA = game.getPlayerA();
 Player playerB = game.getPlayerB();

 game.fireMissile(playerA, playerB);
 game.fireMissile(playerB, playerA);

 game.viewBattleField();
 }
}

About This Question

This is a reported interview question from a square/block interview for a swe role during the system design round reported in 2024.

It covers the following topics: Hash Table, Arrays, Sql, Strings, System Design, Matrix .