Java Record
Java Record
Write a JAVA program to display default value of all primitive data type of JAVA.
give this in a format of 1 aim 2 prerequisites (atleast 10 lines) 3 program 4 out
put
1. Aim
To write a Java program that demonstrates and displays the default values assigned
to each of the eight primitive data types when they are declared as instance
variables without explicit initialization.
2. Prerequisites
Before diving into the program, it's essential to have a foundational understanding
of several core Java concepts. A solid grasp of these prerequisites will make the
program's logic and its output much clearer.
Java Class and Main Method: You should know that every Java application starts with
a class, and the execution begins from the public static void main(String[] args)
method.
Variables: Understand that variables are named memory locations used to store data.
Data Types: In a statically-typed language like Java, every variable must have a
declared type, which determines the kind of data it can hold (e.g., a number, a
character).
Primitive Data Types: Be familiar with Java's eight primitive data types: byte,
short, int, long for integer numbers, float and double for floating-point numbers,
char for single characters, and boolean for true/false values.
Instance Variables vs. Local Variables: This is a crucial concept for this program.
Instance variables are declared inside a class but outside any method. They belong
to an object (an instance) of the class. Java automatically assigns default values
to these variables if they are not explicitly initialized.
Local variables are declared inside a method. They must be explicitly initialized
before they are used, as the compiler does not assign them default values.
Object Creation: You should understand how to create an object from a class using
the new keyword (e.g., ClassName obj = new ClassName();). This is necessary to
access instance variables.
Compilation and Execution: You should have a basic idea of how to compile a .java
file into .class bytecode using javac and how to run the compiled code using the
java command.
3. Program
public class DefaultValues {
// The default char is the null character ('\u0000'), which may not be
visible.
System.out.println("Default value of char is: " + defaultChar);
System.out.println("Default value of char (as integer) is: " +
(int)defaultChar);
4. Output
When you compile and run the above Java program, you will see the following output
on the console:
Note: The default value for char is the null character (\u0000). It has a numeric
value of 0 but doesn't have a visual representation, which is why it prints as a
blank space.
b)Write a java program that display the roots of a quadratic equation ax2+bx=0.
Calculate the
1. Aim
To write a Java program that calculates the roots of a standard quadratic equation
of the form ax² + bx + c = 0. The program will first compute the discriminant (D =
b² - 4ac) and then, based on its value, determine and display the nature of the
roots (whether they are real and distinct, real and equal, or complex).
2. Prerequisites
To fully understand and write this program, you should be familiar with the
following concepts:
The Quadratic Formula: Knowledge of the formula used to find the roots: x = [-b ±
sqrt(b² - 4ac)] / 2a.
Java Variables and Data Types: You should know how to declare variables,
particularly using the double data type to handle decimal values for coefficients
and roots.
User Input in Java: Familiarity with the java.util.Scanner class to read input (the
coefficients a, b, and c) from the user via the console.
Java Math Class: Knowledge of how to use methods from the Math class, specifically
Math.sqrt() to calculate the square root.
Compiling and Running Java Code: A basic ability to compile the .java source file
and run the resulting .class file from the command line.
3. Program
import java.util.Scanner;
System.out.println("\n----------------------------------------");
System.out.println("The discriminant (D) is: " + discriminant);
// Check the value of the discriminant to determine the nature of the roots
if (discriminant > 0) {
// Two real and distinct roots
double root1 = (-b + Math.sqrt(discriminant)) / (2 * a);
double root2 = (-b - Math.sqrt(discriminant)) / (2 * a);
System.out.println("Nature of roots: Real and Distinct");
System.out.format("Root 1 = %.2f%n", root1);
System.out.format("Root 2 = %.2f%n", root2);
} else if (discriminant == 0) {
// Two real and equal roots
double root1 = -b / (2 * a);
// root2 is the same as root1
System.out.println("Nature of roots: Real and Equal");
System.out.format("Root 1 = Root 2 = %.2f%n", root1);
} else {
// No real roots, two complex roots
double realPart = -b / (2 * a);
double imaginaryPart = Math.sqrt(-discriminant) / (2 * a);
System.out.println("Nature of roots: Complex and Distinct");
System.out.format("Root 1 = %.2f + %.2fi%n", realPart, imaginaryPart);
System.out.format("Root 2 = %.2f - %.2fi%n", realPart, imaginaryPart);
}
System.out.println("----------------------------------------");
4. Output
Here are three sample runs of the program, demonstrating the output for each
possible nature of the roots.
----------------------------------------
The discriminant (D) is: 1.0
Nature of roots: Real and Distinct
Root 1 = 3.00
Root 2 = 2.00
----------------------------------------
----------------------------------------
The discriminant (D) is: 0.0
Nature of roots: Real and Equal
Root 1 = Root 2 = -2.00
----------------------------------------
----------------------------------------
The discriminant (D) is: -4.0
Nature of roots: Complex and Distinct
Root 1 = -2.00 + 1.00i
Root 2 = -2.00 - 1.00i
----------------------------------------
Exercise - 2
a) Write a JAVA program to search for an element in a given list of elements using
binary search mechanism.
1. Aim
To write a Java program that implements the binary search algorithm. The program
will search for a user-specified element within a pre-sorted list of elements and
report whether the element is found and, if so, at what index.
2. Prerequisites
A solid understanding of the following concepts is essential to grasp the workings
of the binary search program.
Arrays: You must be comfortable with what arrays are, how to declare and initialize
them in Java, and how to access their elements using indices.
The Binary Search Concept: This is the most critical prerequisite. You must
understand that binary search is a highly efficient searching algorithm that only
works on sorted arrays. It operates on a "divide and conquer" principle.
Licensed by Google
Algorithm Logic: The algorithm repeatedly divides the search interval in half. If
the value of the search key is less than the item in the middle of the interval, it
narrows the interval to the lower half. Otherwise, it narrows it to the upper half.
Loops in Java: The program uses a while loop to continue the search process as long
as the potential search interval is valid (i.e., the low index is less than or
equal to the high index).
Conditional Statements: Mastery of if-else if-else statements is required to
compare the middle element with the target element and decide which half of the
array to search next.
Variables and Pointers: You should understand the use of variables to act as
"pointers" or indices, specifically for the low, high, and mid points of the search
interval.
Methods (Functions): The core search logic is encapsulated in its own method for
modularity and reusability. Understanding how to define, call, and return values
from methods is key.
Return Values: The search method needs to communicate its result back to the
caller. It returns the index of the element if found or a conventional value like -
1 to signify that the element was not present.
Time Complexity: It is helpful to know that binary search has a time complexity of
O(log n), making it significantly faster than linear search (O(n)) for large
datasets.
3. Program
import java.util.Scanner;
/**
* This method performs a binary search on a sorted integer array.
*
* @param arr The sorted array to be searched.
* @param key The element to search for.
* @return The index of the element if found; otherwise, -1.
*/
public static int performBinarySearch(int[] arr, int key) {
int low = 0;
int high = arr.length - 1;
// Continue searching as long as the low index is less than or equal to the
high index
while (low <= high) {
// Calculate mid point to avoid potential overflow
int mid = low + (high - low) / 2;
System.out.println("\n----------------------------------------");
if (result == -1) {
System.out.println("Element " + searchKey + " not found in the
array.");
} else {
System.out.println("Element " + searchKey + " found at index: " +
result);
}
System.out.println("----------------------------------------");
scanner.close();
}
}
4. Output
Here are two sample outputs to show how the program works when an element is found
and when it is not.
----------------------------------------
Element 59 found at index: 4
----------------------------------------
----------------------------------------
Element 30 not found in the array.
----------------------------------------
b) Write a JAVA program to sort for an element in a given list of elements using
bubble sort
1. Aim
To write a Java program that implements the Bubble Sort algorithm to sort a given
list of integer elements in ascending order. The program will display the list both
before and after the sorting process.
2. Prerequisites
To effectively understand and implement the Bubble Sort algorithm in Java, one
should have a strong grasp of the following fundamental concepts:
Bubble Sort Logic: Understand the core mechanism of Bubble Sort. It repeatedly
steps through the list, compares each pair of adjacent items, and swaps them if
they are in the wrong order.
Nested Loops: The algorithm's implementation relies heavily on nested for loops.
The outer loop controls the number of passes through the array, while the inner
loop handles the comparison of adjacent elements.
Variable Swapping: You need to know the standard technique for swapping the values
of two variables, which typically involves using a third, temporary variable.
Java Methods (Functions): It's good practice to encapsulate the sorting logic
within a separate method for better code organization and reusability.
User Input (Scanner Class): To make the program interactive, you should know how to
use the java.util.Scanner class to read the list of elements from the user.
Time Complexity: While not strictly required to write the code, it is beneficial to
know that Bubble Sort has a worst-case and average time complexity of O(n²), making
it inefficient for large datasets.
3. Program
import java.util.Scanner;
import java.util.Arrays;
/**
* This method sorts an integer array using the Bubble Sort algorithm.
*
* @param arr The array to be sorted.
*/
public static void bubbleSort(int[] arr) {
int n = arr.length;
boolean swapped;
System.out.println("\n----------------------------------------");
System.out.println("Original array: " + Arrays.toString(array));
scanner.close();
}
}
4. Output
Here is a sample run of the program showing how it takes an unsorted list and sorts
it.
----------------------------------------
Original array: [64, 34, 25, 12, 22, 11]
Array after Bubble Sort: [11, 12, 22, 25, 34, 64]
----------------------------------------
2. Prerequisites
To fully comprehend this program, a foundational knowledge of the following Java
concepts is recommended:
Java Strings: You must understand that String objects in Java are immutable,
meaning they cannot be changed after they are created.
Mutable vs. Immutable Objects: Grasping the difference between immutable objects
(String) and mutable objects (StringBuffer, StringBuilder) is key to understanding
why StringBuffer is used for modifications.
StringBuffer Class: You should know what the StringBuffer class is and its purpose:
to provide a mutable sequence of characters.
Object Instantiation: Knowledge of how to create an object from a class using the
new keyword (e.g., StringBuffer sb = new StringBuffer("text");).
Method Calling: Familiarity with calling methods on an object using the dot
operator (e.g., sb.delete()).
deleteCharAt(int index) Method: Knowing that this method removes the single
character at the specified index.
delete(int start, int end) Method: Understanding that this method removes the
characters in a substring beginning at the specified start index and extending to
the character at index end - 1.
Console Output: You should know how to use System.out.println() to print text and
variable contents to the console.
Basic Java Program Structure: Familiarity with the public static void main(String[]
args) method and the overall structure of a simple Java class.
3. Program
public class StringBufferDeleteDemo {
4. Output
The following is the exact output produced when the above Java program is compiled
and executed.
Exercise - 3
a) Write a JAVA program to implement class mechanism. Create a class, methods and
invoke them inside main method.
1. Aim
To write a Java program that illustrates the fundamental class and object
mechanism. The goal is to define a custom class with attributes (fields) and
behaviors (methods), then create instances (objects) of that class and invoke their
methods from within the main method.
2. Prerequisites
A solid understanding of the following concepts is essential for grasping the
program's structure and logic.
Class vs. Object: This is the most critical concept. A class is a blueprint or
template for creating objects. An object is a real-world instance of a class.
Methods (Behaviors): These are functions defined inside a class that describe the
actions an object can perform (e.g., a Dog object can bark()).
main Method: Understanding that public static void main(String[] args) is the
special entry point for any Java application. Execution starts here.
Object Instantiation (The new Keyword): You must know how to use the new keyword to
create an object from a class definition (e.g., Dog myDog = new Dog();).
The Dot Operator (.): Knowledge of the dot operator is crucial for accessing an
object's fields and invoking its methods (e.g., myDog.name or myDog.bark()).
Basic Java Syntax: Familiarity with Java's syntax for declaring variables, defining
classes and methods, and using System.out.println() for console output.
3. Program
This program defines a Dog class and then, in the ClassDemo class's main method, it
creates and interacts with two different Dog objects.
/**
* This is the Dog class, which acts as a blueprint for creating Dog objects.
* It has properties (name, breed) and methods (bark, displayInfo).
*/
class Dog {
// Fields (Instance Variables) to store the state of a Dog object
String name;
String breed;
/**
* A method that represents the dog's barking behavior.
*/
public void bark() {
System.out.println(this.name + " says: Woof! Woof!");
}
/**
* A method to display all the information about the dog.
*/
public void displayInfo() {
System.out.println("Dog's Name: " + this.name);
System.out.println("Dog's Breed: " + this.breed);
}
}
/**
* This is the main class that will run the program.
*/
public class ClassDemo {
System.out.println("\n--------------------------------------\n");
System.out.println("\n--------------------------------------");
System.out.println("Program finished.");
}
}
4. Output
The following is the exact output that will be displayed on the console when the
ClassDemo.java program is compiled and executed.
--------------------------------------
--------------------------------------
Program finished.
1. Aim
To write a Java program that demonstrates the concept of method overloading. The
program will define a class containing multiple methods with the same name but
different parameters (in terms of number or data type). The goal is to show how the
Java compiler determines which method to execute based on the arguments passed
during the method call.
2. Prerequisites
To understand and implement method overloading in Java, a firm grasp of the
following concepts is required:
Methods: Understanding that methods are blocks of code that perform a specific task
and are associated with a class.
Method Signature: This is the most crucial concept for overloading. In Java, a
method signature is composed of the method's name and its parameter list (the
number, type, and order of parameters).
Return Type: It's essential to understand that the return type is not part of the
method signature. You cannot overload a method just by changing its return type.
Data Types: A clear understanding of Java's primitive data types (int, double,
etc.) is necessary, as overloading often involves creating methods that accept
different types of data.
Class and Object: The program will be structured within a class, and methods will
be called on an instance (object) of that class.
The main Method: Recognizing that public static void main(String[] args) is the
entry point for the application, from where the overloaded methods will be called.
Method Invocation: Knowing the syntax for calling a method on an object and passing
the required arguments.
Compiler Role: Understanding that the Java compiler is responsible for matching the
method call with the correct method definition based on the arguments provided.
This process is called overload resolution.
3. Program
This program defines a Printer class with multiple display methods. Each display
method has the same name but accepts different types or numbers of parameters.
/**
* This class demonstrates method overloading with a method named 'display'.
*/
class Printer {
/**
* Method to display an integer.
* @param a The integer value to display.
*/
public void display(int a) {
System.out.println("-> Called display(int a)");
System.out.println(" Displaying integer: " + a);
}
/**
* Method to display a String. This is an overload of the display method.
* @param s The String value to display.
*/
public void display(String s) {
System.out.println("-> Called display(String s)");
System.out.println(" Displaying String: \"" + s + "\"");
}
/**
* Method to display an integer and a String. This is another overload.
* @param a The integer value.
* @param s The String value.
*/
public void display(int a, String s) {
System.out.println("-> Called display(int a, String s)");
System.out.println(" Displaying Number: " + a + " and String: \"" + s +
"\"");
}
/**
* Method to display a String and an integer. This is another overload,
* demonstrating that the order of parameters matters.
* @param s The String value.
* @param a The integer value.
*/
public void display(String s, int a) {
System.out.println("-> Called display(String s, int a)");
System.out.println(" Displaying String: \"" + s + "\" and Number: " + a);
}
}
/**
* This is the main class to test the method overloading in the Printer class.
*/
public class MethodOverloadingDemo {
4. Output
The following is the exact output produced when the MethodOverloadingDemo.java
program is compiled and executed.
1. Aim
To write a Java program to implement a constructor for initializing an object's
state.
2. Prerequisites
Understanding constructors requires familiarity with several core Java concepts. A
constructor is a special method that is automatically called when an object of a
class is created. Its primary purpose is to initialize the instance variables of
the new object.
new Keyword: The new keyword is used to allocate memory for a new object and create
an instance of a class.
Constructor Naming Rule: A constructor must have the exact same name as the class
it belongs to.
No Return Type: Unlike other methods, a constructor does not have an explicit
return type, not even void.
Types of Constructors:
Default Constructor: If you don't define any constructor in a class, the Java
compiler provides a default, no-argument constructor.
main method: Understanding that the main method is the entry point for the
execution of any Java application.
3. Program
// We define a class named 'Car'
class Car {
// Instance variables for the Car class
String model;
int year;
// Call the displayDetails method on the myCar object to show its state.
myCar.displayDetails();
}
}
4. Output
Constructor called!
Car Model: Tesla Model S
Car Year: 2023
1. Aim
To write a Java program to implement constructor overloading, which allows a class
to have multiple constructors with different parameter lists.
2. Prerequisites
Constructor overloading is an application of polymorphism in Java. To fully grasp
this concept, one must be familiar with the fundamentals of constructors and method
overloading.
Method Overloading: This is the ability to define multiple methods with the same
name within the same class, as long as their parameter lists differ. The difference
can be in the number of parameters, the data type of parameters, or the order of
parameters.
Compiler's Role: The Java compiler decides which constructor to execute based on
the arguments provided when you create an object using the new keyword. For
example, new Student() would call the no-argument constructor, while new
Student("Alice", 101) would call the constructor that accepts a String and an
integer.
this() keyword (Optional but related): You can use this() to call one constructor
from another within the same class. This is known as constructor chaining and helps
reduce code duplication.
3. Program
// We define a class named 'Student'
class Student {
// Instance variables for the Student class
int studentId;
String studentName;
String grade;
4. Output
No-argument constructor called.
Student ID: 0
Student Name: Unknown
Grade: N/A
--------------------
Two-argument constructor (int, String) called.
Student ID: 101
Student Name: Alice
Grade: 10th
--------------------
Three-argument constructor (int, String, String) called.
Student ID: 102
Student Name: Bob
Grade: 12th
--------------------
Exercise - 4
1. Aim
To write a Java program to implement single inheritance, where a new class
(subclass) is derived from an existing class (superclass), inheriting its fields
and methods.
2. Prerequisites
Understanding single inheritance in Java requires knowledge of fundamental object-
oriented programming (OOP) principles. Inheritance is a core OOP concept that
promotes code reusability and establishes a logical relationship between classes.
Inheritance: It is the mechanism by which one object acquires all the properties
and behaviors of a parent object. This represents an "is-a" relationship. For
example, a Dog is an Animal.
Superclass (Parent/Base Class): The class whose features are inherited. It is the
class being extended.
Subclass (Child/Derived Class): The class that inherits the other class. It can add
its own unique fields and methods.
Code Reusability: Inheritance is a powerful tool for reusing code. The subclass can
directly use the methods and fields of the superclass without rewriting them.
Object Creation: Understanding how to create an instance of the subclass using the
new keyword. An object of the subclass has access to members of both its own class
and its superclass.
3. Program
// Superclass or Parent class
class Animal {
// A method in the superclass
public void eat() {
System.out.println("This animal eats food.");
}
}
4. Output
This animal eats food.
The dog barks.
1. Aim
To write a Java program to implement multilevel inheritance, where a derived class
serves as the base class for another class, forming a chain of inheritance.
2. Prerequisites
Multilevel inheritance builds upon the concept of single inheritance. It involves a
chain of classes, where one class extends another, which in turn extends a third
class. A solid understanding of the following concepts is essential.
Transitive Nature: Inheritance in this model is transitive. The most derived class
(C) inherits all the accessible members not only from its immediate superclass (B)
but also from its grandparent class (A).
"Is-a" Relationship: The "is-a" relationship holds true throughout the chain. Using
the A → B → C example, C is a B, and B is an A.
extends Keyword: This keyword is used at each level of the chain to establish the
parent-child relationship.
3. Program
// The base or 'Grandparent' class
class Vehicle {
public void startEngine() {
System.out.println("Engine has started.");
}
}
4. Output
Engine has started.
The car is moving.
The sports car is accelerating at high speed!
c) Write a JAVA program for abstract class to find areas of different shapes
1. Aim
To write a Java program that demonstrates the use of an abstract class to calculate
the areas of different geometric shapes, enforcing a common structure for all
derived shape classes.
2. Prerequisites
Understanding how to use abstract classes is crucial for leveraging one of the core
principles of Object-Oriented Programming (OOP): Abstraction. This program requires
familiarity with several related concepts.
Abstraction: The concept of hiding complex implementation details and showing only
the essential features of the object. An abstract class is a primary way to achieve
abstraction in Java.
Abstract Class: A class that is declared with the abstract keyword. It cannot be
instantiated, meaning you cannot create an object of an abstract class. It serves
as a blueprint for other classes.
Abstract Method: A method declared with the abstract keyword and without any
implementation (no method body). It exists only as a signature.
Inheritance (extends): Subclasses must extend the abstract class to use its
functionality.
Implementation Mandate: Any subclass that extends an abstract class must provide a
concrete implementation for all of its abstract methods, or the subclass must also
be declared as abstract.
Purpose: Abstract classes are used to define a standard interface or template for a
group of related subclasses, ensuring they all have a common set of methods.
3. Program
// Abstract class 'Shape'
// This class cannot be instantiated directly.
abstract class Shape {
// An abstract method 'calculateArea()'
// It has no body and must be implemented by any subclass.
public abstract double calculateArea();
System.out.println("--------------------");
4. Output
Calculating the area of a shape.
Area of Rectangle: 50.0
--------------------
Calculating the area of a shape.
Area of Circle: 153.93804002589985
Exercise - 5
To invoke a method of the immediate superclass when it has been overridden by the
subclass.
2. Prerequisites
The super keyword in Java is a reference variable that is used to refer to the
immediate parent class object. Its usage is fundamentally tied to the concept of
inheritance. A clear understanding of the following Object-Oriented Programming
(OOP) principles is required.
Inheritance: The mechanism where a new class (subclass) derives properties and
behaviors (fields and methods) from an existing class (superclass). The extends
keyword is used to establish this relationship.
Superclass and Subclass: The class being inherited from is the superclass (or
parent class), and the class that inherits is the subclass (or child class).
Variable Shadowing (or Hiding): If a subclass declares a variable with the same
name as an instance variable in its superclass, the subclass's variable "hides" the
superclass's variable. The super keyword provides a way to access the hidden
variable from the superclass.
this vs. super: While this is a reference to the current object, super is a
reference to the parent part of the current object.
3. Program
// The superclass or 'Parent' class
class Animal {
String type = "Generic Animal";
// Superclass constructor
public Animal() {
System.out.println("Animal class constructor called.");
}
// Superclass method
public void displayInfo() {
System.out.println("This is an animal.");
}
}
// Subclass constructor
public Dog() {
// 1. Use of super() to call the superclass constructor.
// This call is often implicit but shown here for clarity.
super();
System.out.println("Dog class constructor called.");
}
// Overridden method
@Override
public void displayInfo() {
System.out.println("This is a dog.");
}
4. Output
Animal class constructor called.
Dog class constructor called.
1. Aim
To write a Java program that demonstrates how to define and use an interface. The
program will also illustrate how interfaces are Java's mechanism for achieving
multiple inheritance, allowing a single class to inherit behaviors from multiple,
unrelated sources.
2. Prerequisites
Interfaces are a fundamental concept in Java that enable abstraction and a form of
multiple inheritance. To fully grasp their implementation, one must be familiar
with the following principles.
Abstract Methods: By default, all methods declared in an interface are public and
abstract. They have no implementation body.
3. Program
// First interface defining a 'drawable' behavior
interface Drawable {
// Abstract method (public abstract by default)
void draw();
}
4. Output
Drawing a circle with radius: 10.5
LOG: Circle object has been created and drawn successfully.
Drawing a circle with radius: 5.0
1. Aim
To write a Java program that demonstrates runtime polymorphism, also known as
dynamic method dispatch. The program will show how a superclass reference variable
can invoke the overridden methods of different subclass objects at runtime, leading
to different behaviors from the same method call.
2. Prerequisites
Runtime polymorphism is a cornerstone of Object-Oriented Programming (OOP) where
the method to be executed is determined at runtime instead of compile time. A
thorough understanding of the following concepts is essential for grasping its
implementation.
Inheritance: The mechanism where a subclass acquires the properties and methods of
a superclass using the extends keyword. This parent-child relationship is the
foundation for polymorphism.
3. Program
// The superclass or 'Parent' class
class Shape {
// The method to be overridden by subclasses
public void draw() {
System.out.println("Drawing a generic shape.");
}
}
4. Output
Drawing a circle.
Drawing a rectangle.
Drawing a triangle.
Exercise - 6
2. Prerequisites
Exception handling is a critical feature in Java for managing runtime errors and
maintaining the normal flow of an application. To understand its implementation,
familiarity with the following concepts is essential.
try block: This is the block where you place the code that might generate an
exception. It is the section of code to be monitored for errors.
catch block: This block catches and handles the exception. It is executed only if
an exception of the type it specifies occurs within the associated try block. A try
block can be followed by multiple catch blocks to handle different types of
exceptions.
throw keyword: This is used to manually throw an exception, either a new one or one
that has just been caught. It is typically used for custom or explicit error
conditions.
3. Program
public class Main {
/**
* This method attempts to divide two numbers.
* It uses the 'throws' keyword to indicate it might throw an
ArithmeticException
* if the divisor is zero, delegating handling to the caller.
* It also uses the 'throw' keyword to create and throw the exception
explicitly.
*/
public static int divideNumbers(int numerator, int denominator) throws
ArithmeticException {
if (denominator == 0) {
// Manually throwing an exception using the 'throw' keyword.
throw new ArithmeticException("Division by zero is not allowed.");
}
return numerator / denominator;
}
System.out.println("\n----------------------------------------\n");
4. Output
--- Attempting a valid division ---
Entering the try block...
The result of 100 / 5 is: 20
Leaving the try block normally.
This is the finally block. It always runs.
----------------------------------------
1. Aim
To write a Java program that demonstrates the use of multiple catch clauses to
handle different types of exceptions that may arise from a single try block. The
program will show how to provide specific handling logic for each distinct
exception type.
2. Prerequisites
To effectively use multiple catch clauses, a solid understanding of Java's
exception handling hierarchy and mechanism is necessary. The program builds upon
the basic try-catch structure.
Exception Hierarchy: In Java, exceptions are objects that inherit from the
Throwable class. Different runtime errors are represented by different exception
classes (e.g., ArithmeticException, NullPointerException,
ArrayIndexOutOfBoundsException).
try Block: This block encloses the code that is monitored for potential exceptions.
Multiple catch Clauses: A single try block can be followed by several catch blocks.
Each catch block is an exception handler that specifies the type of exception it
can handle.
Execution Flow: When an exception occurs in the try block, the Java runtime system
looks for a matching catch block. It checks the catch blocks in the order they
appear. The first catch block whose parameter type matches the type of the
exception object (or is a superclass of it) is executed. After that one catch block
executes, the others are skipped.
Order of catch Blocks: It is crucial to order the catch blocks from the most
specific exception type to the most general. For instance, a catch for
ArrayIndexOutOfBoundsException must come before a catch for its superclass,
Exception. If the superclass catch comes first, it will handle all related
exceptions, making the more specific subclass catch block unreachable, which
results in a compile-time error.
3. Program
public class Main {
public static void main(String[] args) {
// This program demonstrates two scenarios by changing the code inside the
try block.
System.out.println("\n------------------------------------------------\n");
4. Output
--- Scenario 1: Attempting division by zero ---
Accessing an element: 0
Caught an ArithmeticException!
Error: / by zero
------------------------------------------------
1. Aim
To write a Java program that intentionally triggers and demonstrates the creation
of several common built-in (unchecked) exceptions. The program will show how the
Java Virtual Machine (JVM) automatically throws these exceptions at runtime when
the code violates fundamental language rules, and how they can be handled using
try-catch blocks.
2. Prerequisites
Java provides a robust exception handling framework with a rich set of pre-defined
exception classes, known as built-in exceptions. A clear understanding of these is
essential for writing stable code.
Built-in Exceptions: These are exception classes that are part of the standard Java
API, primarily within the java.lang package. They cover the most common programming
errors.
Checked vs. Unchecked Exceptions: Java exceptions are categorized into two main
types.
Checked Exceptions: These are exceptions that a compiler forces the programmer to
handle (e.g., IOException).
Unchecked Exceptions (Runtime Exceptions): These are exceptions that are not
checked at compile time. They usually stem from logical errors in the code, such as
dividing by zero or accessing a null object. The examples in this program are all
unchecked exceptions.
Exception Hierarchy: All exceptions descend from the java.lang.Throwable class. The
Exception class is a subclass of Throwable, and RuntimeException is a subclass of
Exception. Most built-in, unchecked exceptions are subclasses of RuntimeException.
Automatic Creation: Unlike user-defined exceptions, built-in exceptions are
typically created and thrown automatically by the JVM when it detects an illegal
operation. For example, the JVM itself creates an ArithmeticException object when
it encounters an integer division by zero.
3. Program
public class Main {
public static void main(String[] args) {
// 1. Demonstrating ArithmeticException
try {
System.out.println("1. Trying to divide by zero...");
int result = 30 / 0; // This line creates and throws an
ArithmeticException
} catch (ArithmeticException e) {
System.out.println(" CAUGHT: An ArithmeticException occurred!");
System.out.println(" Exception details: " + e);
}
System.out.println("\n----------------------------------------\n");
// 2. Demonstrating NullPointerException
try {
System.out.println("2. Trying to access a method on a null object...");
String str = null;
System.out.println(str.length()); // This creates and throws a
NullPointerException
} catch (NullPointerException e) {
System.out.println(" CAUGHT: A NullPointerException occurred!");
System.out.println(" Exception details: " + e);
}
System.out.println("\n----------------------------------------\n");
// 3. Demonstrating ArrayIndexOutOfBoundsException
try {
System.out.println("3. Trying to access an invalid array index...");
int[] numbers = new int[5];
System.out.println(numbers[10]); // This creates and throws an
ArrayIndexOutOfBoundsException
} catch (ArrayIndexOutOfBoundsException e) {
System.out.println(" CAUGHT: An ArrayIndexOutOfBoundsException
occurred!");
System.out.println(" Exception details: " + e);
}
System.out.println("\n----------------------------------------\n");
// 4. Demonstrating NumberFormatException
try {
System.out.println("4. Trying to parse an invalid string to an
integer...");
String invalidNumber = "Java";
int num = Integer.parseInt(invalidNumber); // This creates and throws a
NumberFormatException
} catch (NumberFormatException e) {
System.out.println(" CAUGHT: A NumberFormatException occurred!");
System.out.println(" Exception details: " + e);
}
4. Output
1. Trying to divide by zero...
CAUGHT: An ArithmeticException occurred!
Exception details: java.lang.ArithmeticException: / by zero
----------------------------------------
----------------------------------------
----------------------------------------
1. Aim
To write a Java program that defines and uses a custom (user-defined) exception.
The program will create a specific exception class to handle a particular business
logic error—in this case, an invalid age for voting—and then throw and catch this
custom exception.
2. Prerequisites
While Java provides a wide range of built-in exceptions, there are situations where
a custom exception is needed to represent application-specific errors more clearly.
Understanding the following concepts is crucial for creating and using them.
Inheritance: Custom exception classes must extend one of the existing Throwable
subclasses. Typically, you extend java.lang.Exception to create a checked exception
or java.lang.RuntimeException to create an unchecked exception.
The Exception Class: By extending the Exception class, you are creating a custom
checked exception, which the compiler forces you to handle using a try-catch block
or declare with the throws keyword.
The throws Keyword: This keyword is used in a method's signature to declare that
the method might throw one or more specified exceptions. The calling method is then
responsible for handling them.
3. Program
// 1. Create a custom exception class by extending java.lang.Exception
class InvalidAgeException extends Exception {
/**
* This method validates the age. If the age is less than 18,
* it throws our custom InvalidAgeException.
* The 'throws' keyword indicates that this method can throw this exception.
*/
public static void validateAge(int age) throws InvalidAgeException {
if (age < 18) {
// Manually throw our custom exception using the 'throw' keyword
throw new InvalidAgeException("Not eligible to vote: Age must be 18 or
older.");
} else {
System.out.println("Age is valid. Welcome to vote!");
}
}
System.out.println("\n------------------------------------------------\n");
4. Output
--- Scenario 1: Checking a valid age (25) ---
Age is valid. Welcome to vote!
------------------------------------------------
Exercise - 7
a) Write a JAVA program that creates threads by extending Thread class. First
thread display
"Good Morning "every 1 sec, the second thread displays "Hello "every 2 seconds and
the third
1. Aim
To write a Java program that demonstrates the creation and execution of multiple
threads concurrently. The program will be implemented in two ways:
Extending the Thread Class: Creating three threads where the first displays "Good
Morning " every 1 second, the second displays "Hello " every 2 seconds, and the
third displays "Welcome" every 3 seconds.
2. Prerequisites
Understanding multithreading is fundamental to developing responsive and efficient
Java applications. It allows for the parallel execution of different parts of a
program.
Thread Lifecycle: A thread goes through various stages in its life, such as New,
Runnable, Running, Blocked (Waiting), and Terminated. The start() method moves a
thread to the Runnable state.
Creating Threads: Java provides two primary ways to create a thread:
Extending java.lang.Thread: A class can inherit from the Thread class. It must
override the run() method, which contains the logic that the thread will execute.
This approach is simple but less flexible because Java does not support multiple
inheritance.
Key Methods:
run(): Contains the code that constitutes the new thread's task.
sleep(long millis): Pauses the current thread's execution for the specified number
of milliseconds. It throws a checked InterruptedException, which must be handled.
4. Output
(Note: The exact order of output can vary slightly due to the non-deterministic
nature of thread scheduling by the OS. This is a representative example of the
output over approximately 6 seconds.)
4. Output
(The output for the Runnable implementation will be functionally identical to the
Thread extension method, demonstrating interleaved execution. This is a
representative example.)
Use isAlive() to check the execution status of a thread at various points in its
lifecycle.
Use join() to make the main thread wait for the completion of other threads,
ensuring a specific order of execution.
2. Prerequisites
Coordinating the execution of threads is a critical aspect of concurrent
programming. isAlive() and join() are two fundamental methods for managing thread
interactions.
isAlive() Method: This is a final method in the Thread class that tests if a thread
is currently active. It returns true if the thread has been started (its start()
method has been called) and has not yet completed its execution (its run() method
has not finished). It returns false if the thread is in the New state or the
Terminated state.
join() Method: This method causes the current thread (the one calling the method)
to pause its execution until the thread on which join() is invoked completes its
task and terminates. It is essential for scenarios where one thread's work depends
on the result or completion of another.
Thread Scheduling: The order in which threads are executed is determined by the
thread scheduler, which is part of the operating system. Using join() allows a
programmer to impose a specific order on this otherwise non-deterministic process.
3. Program
class WorkerThread extends Thread {
public WorkerThread(String name) {
super(name); // Set the thread's name
}
@Override
public void run() {
System.out.println("-> " + getName() + " has started.");
try {
// Simulate some work by sleeping for 2 seconds
Thread.sleep(2000);
} catch (InterruptedException e) {
System.err.println(getName() + " was interrupted.");
}
System.out.println("<- " + getName() + " has finished.");
}
}
try {
t1.join(); // Main thread pauses here until t1 finishes
System.out.println(t1.getName() + " has joined.");
} catch (InterruptedException e) {
System.err.println("Main thread was interrupted.");
}
4. Output
(Note: The start messages of Worker-1 and Worker-2 might appear in a different
order, but the rest of the output will be consistent due to the join() calls.)
1. Aim
To write a Java program that demonstrates the concept and behavior of a daemon
thread. The program will create a background thread, configure it as a daemon, and
show how its lifecycle is tied to the lifecycle of user threads. The primary goal
is to illustrate that the Java Virtual Machine (JVM) will exit and terminate all
running daemon threads as soon as the last user thread has finished its execution.
2. Prerequisites
Daemon threads are a special kind of thread designed to run in the background,
providing services to user threads. Understanding their unique properties is
essential for correct usage.
User Thread vs. Daemon Thread: By default, every thread created in Java is a "user
thread." The JVM will wait for all user threads to complete their execution before
it shuts down. In contrast, a "daemon thread" is a low-priority thread that runs in
the background. The JVM does not wait for daemon threads to finish.
Purpose: Daemon threads are suitable for background tasks that should not prevent
the application from closing, such as garbage collection, monitoring services, or
auto-saving functionality.
setDaemon(boolean on) Method: This Thread class method is used to mark a thread as
a daemon thread. It is crucial to call this method before the thread is started
(i.e., before calling the start() method). Attempting to set it after the thread
has started will result in an IllegalThreadStateException.
isDaemon() Method: This method returns true if the thread is a daemon thread, and
false otherwise.
JVM Shutdown: The key takeaway is that an application terminates when its last user
thread completes. At this point, any remaining daemon threads are abruptly stopped
and abandoned, regardless of what they are doing. Their finally blocks are not
guaranteed to execute, so they should not be used for critical I/O operations.
3. Program
class BackgroundWorker extends Thread {
@Override
public void run() {
// This is an infinite loop to simulate a long-running background task.
// We will check if the thread is a daemon or a user thread.
if (isDaemon()) {
System.out.println("-> Daemon thread has started its background
work.");
} else {
System.out.println("-> User thread has started its work.");
}
try {
while (true) {
System.out.println(" Background task is running...");
Thread.sleep(1000); // Pauses for 1 second
}
} catch (InterruptedException e) {
// This part is unlikely to be reached in this example because the
// thread will be terminated abruptly.
System.err.println("Thread was interrupted.");
} finally {
// IMPORTANT: Finally blocks are NOT guaranteed to run for daemon
threads
// when the JVM exits.
System.out.println(" Daemon thread's finally block.");
}
}
}
try {
// The main thread will do some work and then finish.
// Let's make it sleep for 3 seconds to allow the daemon thread to run
for a bit.
System.out.println("Main thread is sleeping for 3 seconds...");
Thread.sleep(3000);
} catch (InterruptedException e) {
System.err.println("Main thread was interrupted.");
}
// Once the main thread finishes, the JVM will see that only daemon threads
// are left running, so it will exit, terminating the daemon thread.
System.out.println("Main thread is finishing. JVM will now exit.");
}
}
4. Output
(The output demonstrates that the daemon thread is abruptly terminated when the
main thread finishes. Notice the absence of the "finally block" message.)
1. Aim
To write a Java program that implements a solution to the classic Producer-Consumer
synchronization problem. The program will use a shared, fixed-size buffer and
utilize synchronized methods along with inter-thread communication mechanisms
(wait() and notify()) to ensure that:
The producer does not add data to the buffer when it is full.
The consumer does not try to remove data from the buffer when it is empty.
Both threads can operate concurrently without causing data corruption or race
conditions.
2. Prerequisites
The Producer-Consumer problem is a cornerstone of concurrent programming, and its
solution requires a solid understanding of thread synchronization and
communication.
The Problem Statement: It involves two types of processes, producers and consumers,
who share a common, fixed-size buffer. Producers generate data and put it into the
buffer. Consumers remove data from the buffer and process it. The challenge is to
manage this process so the buffer is accessed safely.
Synchronization: To prevent race conditions where both threads might try to modify
the buffer simultaneously, access to the shared buffer must be synchronized. This
is achieved by placing the logic for adding and removing items into synchronized
methods or blocks, ensuring only one thread can execute them at any given time.
wait(): This method, called on an object lock, tells the calling thread to release
the lock and go into a waiting state. A producer will wait() if the buffer is full,
and a consumer will wait() if the buffer is empty.
notify(): This method wakes up a single thread that is waiting on the same object
lock. When a producer adds an item, it calls notify() to wake up a waiting
consumer. When a consumer removes an item, it calls notify() to wake up a waiting
producer.
wait() and notify() Rules: These methods must be called from within a synchronized
context (a block or method synchronized on the same object).
Spurious Wakeups: A waiting thread can sometimes wake up without being explicitly
notified. To guard against this, the condition for waiting (e.g., buffer.isFull())
must always be checked within a while loop, not an if statement.
3. Program
import java.util.LinkedList;
import java.util.Queue;
/**
* This class represents the shared buffer between the Producer and Consumer.
* It has a fixed capacity and synchronized methods for producing and consuming
items.
*/
class SharedBuffer {
private final Queue<Integer> buffer;
private final int capacity;
/**
* Producer calls this method to put an item into the buffer.
* The method is synchronized to ensure thread safety.
* @param item The integer item to be produced.
* @throws InterruptedException if the thread is interrupted while waiting.
*/
public synchronized void produce(int item) throws InterruptedException {
// Use a while loop to check the condition to handle spurious wakeups.
while (buffer.size() == capacity) {
System.out.println("Buffer is full. Producer is waiting...");
wait(); // Release the lock and wait until notified.
}
buffer.add(item);
System.out.println("Produced: " + item + " [Buffer size: " + buffer.size()
+ "]");
/**
* Consumer calls this method to get an item from the buffer.
* The method is synchronized to ensure thread safety.
* @return The integer item consumed.
* @throws InterruptedException if the thread is interrupted while waiting.
*/
public synchronized int consume() throws InterruptedException {
// Use a while loop to check the condition.
while (buffer.isEmpty()) {
System.out.println("Buffer is empty. Consumer is waiting...");
wait(); // Release the lock and wait until notified.
}
/**
* The Producer thread, which produces items and puts them in the shared buffer.
*/
class Producer implements Runnable {
private final SharedBuffer buffer;
@Override
public void run() {
try {
for (int i = 1; i <= 10; i++) {
buffer.produce(i);
Thread.sleep(100); // Simulate time taken to produce an item
}
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
}
}
}
/**
* The Consumer thread, which consumes items from the shared buffer.
*/
class Consumer implements Runnable {
private final SharedBuffer buffer;
@Override
public void run() {
try {
for (int i = 0; i < 10; i++) {
buffer.consume();
Thread.sleep(250); // Simulate time taken to consume an item
}
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
}
}
}
4. Output
(Note: The exact timing and interleaving of the output can vary slightly due to
thread scheduling, but the logic will be consistent. This is a representative
example.)
Exercise -8
a) Write a JAVA program that import and use the user defined packages
1. Aim
To write a Java program that demonstrates the creation, compilation, and usage of a
user-defined package. The program will consist of two parts:
A Main class in the default package that imports and utilizes the Calculator class
to perform operations.
2. Prerequisites
Packages are a fundamental feature in Java for organizing and encapsulating classes
and interfaces. They are essential for creating modular, reusable, and manageable
codebases.
package Keyword: To place a class inside a package, the package statement must be
the very first line of the source code file.
Directory Structure: This is the most crucial aspect. Java uses the file system to
manage packages. A package named mypack.tools must have its corresponding .java
files inside a directory structure mypack/tools/. The compiler and JVM rely on this
structure to locate the necessary files.
import Keyword: To use a class from another package, you must import it using the
import keyword. You can import a specific class (e.g., import
mypack.tools.Calculator;) or all classes in a package (e.g., import
mypack.tools.*;).
Compilation (javac -d): When compiling classes that belong to a package, the javac
compiler's -d option is used. It specifies the destination directory for the
generated .class files, automatically creating the required package folder
structure.
Classpath: The classpath is the path where the Java Virtual Machine (JVM) and the
Java compiler search for .class files. The current directory (.) is usually on the
classpath by default, which is why the -d . command works.
3. Program
This program requires two separate files and a specific folder structure.
First, create a main project folder (e.g., PackageDemo). Inside it, create the
directory structure for our package mypack/tools. Your final structure will look
like this:
PackageDemo/
├── mypack/
│ └── tools/
│ └── Calculator.java
└── Main.java
This file defines our Calculator class and places it in the mypack.tools package.
// File: PackageDemo/mypack/tools/Calculator.java
package mypack.tools;
This is our main program that will import and use the Calculator class.
// File: PackageDemo/Main.java
Compile the Calculator.java file. The -d . command tells the compiler to create the
.class files in the correct package directory structure within the current folder
(.).
javac -d . mypack/tools/Calculator.java
Compile the Main.java file. The compiler will automatically find the
Calculator.class file because it's in the correct directory structure.
javac Main.java
java Main
4. Output
After executing the java Main command, you will see the following output on your
console:
(use JavaFX)
1. Aim
To design a Graphical User Interface (GUI) in JavaFX that displays a text label and
an image. The entire user interface will be defined declaratively using FXML,
demonstrating the separation of the UI's appearance (the "View") from the
application's logic (the "Controller"). This fulfills the requirement of building a
GUI without writing procedural Java code for the layout itself.
2. Prerequisites
To understand this approach, one must be familiar with the JavaFX platform and its
declarative UI definition language, FXML.
JavaFX: The modern, official framework for building rich client applications in
Java. It replaces the older Swing toolkit.
Separation of Concerns (MVC Pattern): FXML allows for a clean separation of the
user interface (View) from the application logic (Controller) and data (Model). The
FXML file exclusively handles the layout and appearance.
Scene Builder: A visual layout tool for JavaFX. Scene Builder allows you to drag
and drop UI components to design an FXML file without writing the XML markup by
hand. It is the ultimate "no code" tool for creating Java GUIs.
Layout Panes: These are containers that manage the arrangement of UI components.
For this example, we will use a VBox, which arranges its children in a single
vertical column.
UI Controls: The visual components the user interacts with. We will use:
FXMLLoader: While the FXML itself contains no procedural code, a minimal Java
application is required to load the FXML file and display it on the screen. The
FXMLLoader class is responsible for parsing the FXML source file and creating the
live UI object graph from it.
<!--
Import the necessary JavaFX classes. This is similar to 'import' in Java.
We need VBox for the layout, Label for the text, and ImageView/Image for the
picture.
-->
<?import javafx.scene.layout.VBox?>
<?import javafx.scene.control.Label?>
<?import javafx.scene.image.ImageView?>
<?import javafx.scene.image.Image?>
<?import javafx.geometry.Insets?>
<?import javafx.scene.text.Font?>
<!--
The root element is a VBox. It arranges its children vertically.
'alignment="CENTER"' centers the content horizontally.
'spacing="20"' adds 20 pixels of vertical space between the label and the image.
-->
<VBox xmlns:fx="[http://javafx.com/fxml/1](http://javafx.com/fxml/1)"
alignment="CENTER" spacing="20">
<!-- Add padding of 25 pixels around the entire VBox container -->
<padding>
<Insets top="25" right="25" bottom="25" left="25"/>
</padding>
<!--
This is the Label component.
- 'text' property sets the displayed text.
- 'font' tag sets the font size to 24.
-->
<Label text="A Beautiful Landscape from the Web">
<font>
<Font name="Arial Bold" size="24"/>
</font>
</Label>
<!--
This is the ImageView component that will display the image.
- 'fitWidth' sets the desired width of the view.
- 'preserveRatio="true"' ensures the image is not distorted when resized.
-->
<ImageView fitWidth="500" preserveRatio="true">
<image>
<!--
The Image object is created here. The 'url' attribute points to an
image on the internet. Using a URL avoids needing a local file.
-->
<Image url="[https://placehold.co/600x400/42a5f5/ffffff?
text=Sample+Image](https://placehold.co/600x400/42a5f5/ffffff?
text=Sample+Image)" />
</image>
</ImageView>
</VBox>
4. Output
When the DisplayUI.fxml file is loaded by a JavaFX application, it will produce a
window with the following appearance:
Below the text, with a 20-pixel gap, a 500-pixel-wide image will be displayed. The
image will be a placeholder graphic with the text "Sample Image" on a blue
background.
The entire content will have a 25-pixel padded border inside the window.
c) Build a Tip Calculator app using several JavaFX components and learn how to
respond to user interactions with the GUI
1aim:
Create a complete graphical user interface (GUI) using the JavaFX framework.
Use several common components like Label, TextField, Slider, and Button.
Update the GUI in real-time by calculating the tip and total bill when the user
interacts with the app.
Of course. Here are the prerequisites for building the JavaFX Tip Calculator
application.
2Prerequisites
To understand and build this application, familiarity with several core JavaFX
concepts is required. These concepts form the foundation of creating interactive
and well-structured graphical user interfaces in Java.
JavaFX Application Structure: You need to understand that every JavaFX application
extends the Application class and implements the start(Stage primaryStage) method.
This method is the main entry point for the GUI, where the Stage represents the
main window.
Scene Graph: The GUI is structured as a tree of nodes. A Scene object is created to
contain the root node of this tree (in our case, a VBox), which is then set on the
Stage.
Layout Panes: These are containers that organize the UI components. For this app,
you need to know about:
GridPane: Arranges its children in a flexible grid of rows and columns, which is
perfect for neatly aligning labels with their corresponding input fields.
UI Controls: You should be familiar with the basic interactive elements of a GUI.
The ones used in this program are:
TextField: Allows the user to enter a single line of text (for the bill amount).
Slider: Lets the user select a value from a continuous range by dragging a thumb
(for the tip percentage).
Button: A control that triggers an action when clicked.
Event Handling: This is the most critical part for making the application
interactive. You must understand how to respond to user actions:
Data Conversion & Formatting: A practical application requires handling data. You
should know how to:
Convert a String from a TextField into a numeric type like double (e.g., using
Double.parseDouble()).
Handle potential errors, like the NumberFormatException if the user enters non-
numeric text.
Format numeric output neatly, for instance, using the DecimalFormat class to
display values as currency (e.g., "$24.10").
import javafx.application.Application;
import javafx.geometry.Insets;
import javafx.geometry.Pos;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.control.Label;
import javafx.scene.control.Slider;
import javafx.scene.control.TextField;
import javafx.scene.layout.GridPane;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;
import java.text.DecimalFormat;
@Override
public void start(Stage primaryStage) {
primaryStage.setTitle("Tip Calculator");
// Input components
TextField billAmountField = new TextField();
billAmountField.setPromptText("Enter total bill");
Slider tipSlider = new Slider(0, 30, 15); // Min: 0%, Max: 30%, Default:
15%
tipSlider.setShowTickLabels(true);
tipSlider.setShowTickMarks(true);
tipSlider.setMajorTickUnit(5);
Button calculateButton = new Button("Calculate Tip");
inputGrid.add(billAmountLabel, 0, 0);
inputGrid.add(billAmountField, 1, 0);
inputGrid.add(tipPercentageLabel, 0, 1);
inputGrid.add(tipSlider, 1, 1);
inputGrid.add(tipPercentageValueLabel, 2, 1); // Add the percentage display
next to the slider
// Perform calculations
double tipAmount = billAmount * (tipPercentage / 100.0);
double totalAmount = billAmount + tipAmount;
} catch (NumberFormatException e) {
// Handle invalid input (e.g., non-numeric text)
tipResultLabel.setText("Error!");
totalResultLabel.setText("Please enter a valid bill amount.");
}
});
// --- Scene and Stage Setup ---
Scene scene = new Scene(root, 400, 450);
primaryStage.setScene(scene);
primaryStage.show();
}