GitHunt
TA

taruncse/PracticalTestBongo

PracticalTestBongo

Q1) Write a function that detects if two strings are anagram e.g. ‘bleat’ and ‘table’ are anagrams but ‘eat’ and ‘tar’ are not.

Answer :

  • Anagram.java class
import java.util.Arrays;

public class Anagram {
    static boolean isAnagram(String firstString, String secondString)
    {
        if (firstString == null || secondString == null || firstString.length()==0 || secondString.length()==0 ||
                (firstString.length() != secondString.length()))
            return false;

        int ARRAY_COUNT = 256;

        char firstArray[] = firstString.toLowerCase().toCharArray();
        char secondArray[] = secondString.toLowerCase().toCharArray();

        int firstCounter[] = new int[ARRAY_COUNT];
        Arrays.fill(firstCounter, 0); // set default value

        int secondCounter[] = new int[ARRAY_COUNT];
        Arrays.fill(secondCounter, 0); // set default value

        for (int i = 0; i < firstArray.length; i++) {
            firstCounter[firstArray[i]]++;
            secondCounter[secondArray[i]]++;
        }

        for (int j = 0; j < ARRAY_COUNT; j++)
            if (firstCounter[j] != secondCounter[j]) // match the count values
                return false;

        return true;
    }
}
  • Main method , from where the Anagram method will be called
public class Main {

    public static void main(String[] args) {

        Scanner sc = new Scanner(System.in);

        System.out.println("Enter first String");
        String firstString = sc.nextLine();

        System.out.println("Enter second String");
        String secondString = sc.nextLine();

        if (Anagram.isAnagram(firstString, secondString)){
            System.out.println(firstString+" and "+secondString+" two strings are anagram");
        } else{
            System.out.println(firstString+" and "+secondString+" two strings are not anagram");
        }
    }
}
  • Anagram Test code
import org.junit.Test;

import static org.junit.Assert.*;

public class AnagramTest extends Anagram {

    @Test
    public void nullTest() {
        boolean testNull = Anagram.isAnagram(null,null);
       assertEquals(false,testNull);
    }

    @Test
    public void emptyStringTest() {
        boolean testEmptyString = Anagram.isAnagram("","");
        assertEquals(false,testEmptyString);
    }

    @Test
    public void emptyStringAndNullTest() {
        boolean testEmptyAndNullString = Anagram.isAnagram(null,"");
        assertEquals(false,testEmptyAndNullString);
    }
    @Test
    public void anagramTest() {
        boolean testAnagram = Anagram.isAnagram("bleat","table");
        assertEquals(true,testAnagram);
    }

    @Test
    public void notAnagramTest() {
        boolean testWrongAnagram = Anagram.isAnagram("eat","tar");
        assertEquals(false,testWrongAnagram);
    }
    @Test
    public void largeStringTest() {
        boolean testLargeText = Anagram.isAnagram("Hi this is a large string to test anagram. If the test is fails then there is a problem"
                ,"Hi this is a large string to test anagram. If the test is fails then there is a problem");
        assertEquals(true,testLargeText);
    }
}

Q2) Explain the design pattern used in following:

interface Vehicle {
	int set_num_of_wheels()
	int set_num_of_passengers()
	boolean has_gas()
}

2a) Explain how can you use the pattern to create car and plane class?

Answer :

We can use this interface directly as the normal interface is used.

Given Interface Vehicle

public interface Vehicle {
    int set_num_of_wheels();
    int set_num_of_passengers();
    boolean has_gas();
}
  • Vehicle interface has been implemented in Car class, and default values are assigned.
public class Car implements Vehicle {
    @Override
    public int set_num_of_wheels() {
        return 4;
    }

    @Override
    public int set_num_of_passengers() {
        return 6;
    }

    @Override
    public boolean has_gas() {
        return true;
    }
}
  • Vehicle interface has been implemented in Plane class, and default values are assigned.
public class Plane implements Vehicle {
    @Override
    public int set_num_of_wheels() {
        return 6;
    }

    @Override
    public int set_num_of_passengers() {
        return 200;
    }

    @Override
    public boolean has_gas() {
        return false;
    }
}
  • VehicleProvider class
public class VehicleProvider {
    public Vehicle getCar(){
        return new Car();
    }

    public Vehicle getPlane(){
        return new Plane();
    }
}
  • Main method and entry point of the programm
import basic.VehicleProvider;

public class Main {

    public static void main(String[] args) {
        VehicleProvider vehicleProvider = new VehicleProvider();

        Vehicle plane = vehicleProvider.getPlane();
        printValue(plane);

        Vehicle car = vehicleProvider.getCar();
        printValue(car);

    }

    private static void printValue(Vehicle vehicle){
        System.out.print(vehicle.getClass().getSimpleName()+":\n Has gas: "+vehicle.has_gas()+
                "\n Number of Passengers: "+vehicle.set_num_of_passengers()+
                "\n Number of wheels: "+vehicle.set_num_of_wheels()+"\n");
    }
}

2b) Use a different design pattern for this solution.

Answer : For the different solution , I would use Simple factory pattern . Because , a interface is given to build two types of
object like Car and Plane. This types of scenario will be a perfect match with Simple factory pattern . And we would be able to change
the value of the object on the fly.

Given Interface Vehicle

public interface Vehicle {
    int set_num_of_wheels();
    int set_num_of_passengers();
    boolean has_gas();
}
  • Car class
import basic.Vehicle;

public class Car implements Vehicle {
    int num_of_wheels,num_of_passengers;
    boolean has_gas;
    public Car(int num_of_passengers, int num_of_wheels, boolean has_gas){
        this.num_of_passengers = num_of_passengers;
        this.num_of_wheels = num_of_wheels;
        this.has_gas = has_gas;
    }
    @Override
    public int set_num_of_wheels() {
        return num_of_wheels;
    }

    @Override
    public int set_num_of_passengers() {
        return num_of_passengers;
    }

    @Override
    public boolean has_gas() {
        return has_gas;
    }
}
  • Plane class
import basic.Vehicle;

public class Plane implements Vehicle {

    int num_of_wheels,num_of_passengers;
    boolean has_gas;
    public Plane(int num_of_passengers, int num_of_wheels, boolean has_gas){
        this.num_of_passengers = num_of_passengers;
        this.num_of_wheels = num_of_wheels;
        this.has_gas = has_gas;
    }
    @Override
    public int set_num_of_wheels() {
        return num_of_wheels;
    }

    @Override
    public int set_num_of_passengers() {
        return num_of_passengers;
    }

    @Override
    public boolean has_gas() {
        return has_gas;
    }
}
  • Factory class
import basic.Vehicle;

public class VehicleFactory {
    public static Vehicle createCar ( int num_of_wheels,int num_of_passengers,
            boolean has_gas){
        return new Car(num_of_passengers, num_of_wheels, has_gas);
    }

    public static Vehicle createPlane ( int num_of_wheels,int num_of_passengers,
                                      boolean has_gas){
        return new Plane(num_of_passengers, num_of_wheels, has_gas);
    }
}

Main entry point to test the pattern

import factory.VehicleFactory;

public class Main {

    public static void main(String[] args) {
     
        Vehicle car = VehicleFactory.createCar(4,6,true);
        printValue(car);

        Vehicle plane = VehicleFactory.createPlane(6,200,false);
        printValue(plane);
    }

    private static void printValue(Vehicle vehicle){
        System.out.print(vehicle.getClass().getSimpleName()+":\n Has gas: "+vehicle.has_gas()+
                "\n Number of Passengers: "+vehicle.set_num_of_passengers()+
                "\n Number of wheels: "+vehicle.set_num_of_wheels()+"\n");
    }
}

Q3. Write a video player application with ‘Play’, ‘Forward’ , ‘Rewind’ functionalities. Please write pseudocode for this program and explain the design pattern you will use to develop these three functionalities.

Answer:

I think Facade design pattern can be used to build this entire application. Sometimes it seems that Command Pattern would be more suited as the play/pause functionality is under the same button. But Facade will be more suited here than Command pattern.

The sudo code is given bellow.

  • activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">

    <TextView
        android:id="@+id/txtDisplay"
        android:layout_width="257dp"
        android:layout_height="50dp"
        android:text="This is a player!"
        android:gravity="center"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toTopOf="parent"
        app:layout_constraintVertical_bias="0.13" />

    <Button
        android:id="@+id/btnPlay"
        android:layout_width="53dp"
        android:layout_height="45dp"
        android:layout_marginStart="8dp"
        android:layout_marginTop="48dp"
        android:layout_marginEnd="8dp"
        android:background="@android:color/transparent"
        android:drawableTop="@drawable/play"
        app:layout_constraintEnd_toStartOf="@+id/btnForward"
        app:layout_constraintHorizontal_bias="0.495"
        app:layout_constraintStart_toEndOf="@+id/btnBack"
        app:layout_constraintTop_toBottomOf="@+id/txtDisplay" />

    <Button
        android:id="@+id/btnBack"
        android:layout_width="59dp"
        android:layout_height="42dp"
        android:layout_marginStart="16dp"
        android:layout_marginTop="48dp"
        android:background="@android:color/transparent"
        android:drawableTop="@drawable/rewind"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@+id/txtDisplay" />

    <Button
        android:id="@+id/btnForward"
        android:layout_width="65dp"
        android:layout_height="44dp"
        android:layout_marginTop="48dp"
        android:layout_marginEnd="16dp"
        android:background="@android:color/transparent"
        android:drawableTop="@drawable/forward"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintTop_toBottomOf="@+id/txtDisplay" />

</androidx.constraintlayout.widget.ConstraintLayout>
  • PlayerFunction interface.
public interface PlayerFunction {
    boolean hasExternalStorage();
    String getVideoPath();
    int getVideoSize();
}
  • PlayerInterface
public interface PlayerInterface {
    void play();
    void pause();
    void forward();
    void rewind();
}
  • Update view interface
public interface UpdateView {
    void update(String value);
}

Constants class for constant values

public class Constants {
    public static String PLAY_TAG = "Play";
    public static String PAUSE_TAG = "Pause";

    public static String PLAY = "Playing...";
    public static String PAUSE = "Paused...";
    public static String REWIND = "Rewind...";
    public static String FORWARD = "Forward...";

}
  • Player class
public class Player implements PlayerFunction{
    @Override
    public boolean hasExternalStorage() {
        return false;
    }

    @Override
    public String getVideoPath() {
        return null;
    }

    @Override
    public int getVideoSize() {
        return 0;
    }
}
  • PlayerFacade class
public class PlayerFacade implements PlayerInterface{
    protected  Player player;
    Update update;
    public PlayerFacade(Player player, Update update){
        this.player = player;
        this.update = update;
    }

    @Override
    public void play() {
        player.getVideoPath();
        player.getVideoSize();
        player.hasExternalStorage();
        update.update(Constants.PLAY);
    }

    @Override
    public void pause() {
        player.getVideoPath();
        update.update(Constants.PAUSE);

    }

    @Override
    public void forward() {
        player.getVideoPath();
        update.update(Constants.FORWARD);

    }

    @Override
    public void rewind() {
        player.getVideoPath();
        update.update(Constants.REWIND);
    }
}
  • MainActivity is the entry point of the programm
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.content.ContextCompat;

import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;

public class MainActivity extends AppCompatActivity implements View.OnClickListener, UpdateView{

    Button btnPlay,btnBack,btnForward;
    TextView txtDisplay;
    PlayerInterface player;
    Drawable pauseDrawable,playDrawable;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        initialization();
    }

    private void initialization() {
        btnBack = findViewById(R.id.btnBack);
        btnForward = findViewById(R.id.btnForward);
        btnPlay = findViewById(R.id.btnPlay);

        txtDisplay = findViewById(R.id.txtDisplay);

        btnPlay.setOnClickListener(this);
        btnForward.setOnClickListener(this);
        btnBack.setOnClickListener(this);

        setTag(Constants.PLAY_TAG);
        player = new PlayerFacade(new Player(),this);

        pauseDrawable =  ContextCompat.getDrawable(this, R.drawable.pause);
        playDrawable =  ContextCompat.getDrawable(this, R.drawable.play);

        changeImage(playDrawable);

    }

    @Override
    public void update(String value) {
        txtDisplay.setText(value);
    }

    @Override
    public void onClick(View v) {
        switch(v.getId()){
            case R.id.btnBack:
                player.rewind();
                break;
            case R.id.btnForward:
                player.forward();
                break;
            case R.id.btnPlay:
                if (btnPlay.getTag().equals(Constants.PLAY_TAG)){
                    setTag(Constants.PAUSE_TAG);
                    player.play();
                    changeImage(pauseDrawable);
                }else {
                    setTag(Constants.PLAY_TAG);
                    player.pause();
                    changeImage(playDrawable);
                }
                break;
        }
    }

    private void setTag(String tag){
        btnPlay.setTag(tag);
    }

    private void changeImage(Drawable img){
        btnPlay.setCompoundDrawablesWithIntrinsicBounds(null, img , null, null);
    }
}