0882 Learning Java Language PDF
0882 Learning Java Language PDF
#java
Table of Contents
About 1
Remarks 2
Installing Java 3
What's next? 3
Testing 3
Other 3
Versions 4
Examples 4
Introduction 11
Examples 11
Remarks 14
Examples 14
More examples: 16
Nore examples: 19
Introduction 25
Syntax 25
Remarks 25
Parameter types 25
Examples 25
Built-in annotations 25
Default values 30
Meta-Annotations 30
@Target 30
Available Values 30
@Retention 31
Available values 32
@Documented 32
@Inherited 32
@Repeatable 32
Repeating Annotations 33
Inherited Annotations 35
Example 35
The annotation 36
Packaging 38
IDE integration 39
Netbeans 39
Result 39
The idea behind Annotations 40
Examples 42
Introduction 45
Examples 45
Chapter 7: Applets 47
Introduction 47
Remarks 47
Examples 47
Minimal Applet 47
Creating a GUI 48
Chapter 8: Arrays 52
Introduction 52
Syntax 52
Parameters 52
Examples 52
Basic cases 52
Arrays, Collections, and Streams 53
Intro 53
Arrays to a String 61
ArrayIndexOutOfBoundsException 66
Arrays to Stream 68
Copying arrays 71
for loop 71
Object.clone() 71
Arrays.copyOf() 72
System.arraycopy() 72
Arrays.copyOfRange() 72
Casting Arrays 73
Using ArrayList 73
Using System.arraycopy 74
Array Covariance 74
Using a Stream 77
Sorting arrays 78
Chapter 9: Asserting 81
Syntax 81
Parameters 81
Remarks 81
Examples 81
Introduction 82
Parameters 82
Remarks 82
Examples 82
Remarks 87
Examples 87
Introduction 91
Remarks 91
Examples 91
Remarks 96
Examples 96
For Loops 97
While Loops 98
do...while Loop 98
For Each 98
If / Else 99
Break 102
Introduction 105
Examples 105
Simple JMH example 105
Introduction 108
Examples 108
1.Addition 108
2.Subtraction 109
3.Multiplication 109
4.Division 109
6.Power 110
7.Max 111
8.Min 111
BigDecimal.valueOf() 113
Introduction 114
Syntax 114
Remarks 114
Examples 115
Initialization 115
Examples 122
Checking, setting, clearing, and toggling individual bits. Using long as bit mask 123
Syntax 128
Remarks 128
Examples 128
Introduction 130
Syntax 130
Examples 130
Examples 133
Introduction 140
Remarks 140
C++ 140
Java 140
C++ 140
Java 141
C++ 141
Java 141
Polymorphism 142
Examples 145
C++ 146
Java 146
C++ 146
Java 147
C++ 147
Java 147
C++ 149
Java 149
C++ 150
Java 150
Interface 150
C++ 150
Java 150
Remarks 151
Examples 151
Examples 153
Introduction 155
Examples 155
Introduction 156
Examples 156
Introduction 157
Syntax 157
Examples 157
Constructors 162
Remarks 167
Examples 167
Introduction 170
Syntax 170
Parameters 170
Examples 170
Introduction 172
Remarks 172
Examples 173
INCORRECT 176
CORRECT 177
Creating your own Iterable structure for use with Iterator or for-each loop. 184
Syntax 188
Parameters 188
Remarks 188
Examples 188
Introduction 192
Examples 192
The equality operator does NOT test that two objects are equal 200
Syntax 204
Remarks 204
Examples 204
Introduction 212
Examples 212
Introduction 214
Examples 214
Thread-safe Collections 214
Introduction 218
Remarks 218
Examples 218
Producer-Consumer 219
CountDownLatch 221
Synchronization 223
Semaphore 237
Get status of all threads started by your program excluding system threads 239
Examples 244
Introduction 249
Remarks 249
Examples 249
Examples 253
Remarks 259
Examples 259
Examples 266
Syntax 267
Parameters 267
Remarks 267
Examples 268
LocalTime 277
Examples 278
Instant 279
Syntax 283
Remarks 283
References : 284
Examples 284
Introduction 290
Remarks 290
Examples 290
Syntax 292
Parameters 292
Examples 292
Introduction 300
Syntax 300
Remarks 301
Examples 301
Links 303
Introduction 307
Remarks 307
Examples 307
Introduction 310
Remarks 310
Examples 310
Introduction 313
Examples 313
Introduction 314
Examples 314
Introduction 315
Syntax 315
Remarks 315
Restrictions 315
Tips & Tricks 315
Examples 316
By default: 328
Introduction 334
Examples 334
Introduction 335
Syntax 335
Examples 335
Introduction 352
Try-finally 357
try-catch-finally 357
Introduction 361
Remarks 361
Examples 361
ThreadPoolExecutor 362
Introduction 374
Remarks 374
Examples 374
Introduction 381
Examples 381
Locking 389
Introduction 397
Examples 397
Remarks 400
Examples 400
Syntax 403
Parameters 403
Examples 403
Introduction 409
Examples 409
Examples 412
Introduction 413
Syntax 413
Remarks 413
Examples 413
Note: 423
Workarounds 423
Referring to the declared generic type within its own declaration 424
Different ways for implementing a Generic Interface (or extending a Generic Class) 426
Introduction 430
Examples 430
Introduction 434
Examples 434
Hashtable 434
Remarks 435
Examples 435
Explanation: 438
Example: 438
Introduction 439
Remarks 439
Examples 439
Remarks 442
Examples 442
Typical design flaws which prevent a class from being immutable 444
Introduction 448
Syntax 448
Remarks 448
Examples 448
Inheritance 453
Abstract class and Interface usage: "Is-a" relation vs "Has-a" capability 460
Syntax 465
Remarks 465
Examples 465
Introduction 470
Examples 470
Assumptions: 470
Introduction 482
Syntax 482
Examples 482
Variables 492
Methods 492
Introduction 494
Remarks 494
Examples 494
Examples 498
Remarks 501
Examples 501
References 504
Introduction 506
Remarks 506
Examples 506
Creating JAR, WAR and EAR files using the jar command. 508
Prerequisites 509
Examples 513
Differences between Java EE, Java SE, Java ME and JavaFX 514
Java SE 515
Java EE 515
Java ME 515
Java FX 516
Introduction 519
Examples 519
Remarks 524
Examples 524
Finalization 524
Remarks 531
Examples 531
Actions 534
Examples 539
Parameters 541
Remarks 541
Examples 541
Output 543
Output 544
Examples 547
Introduction 550
Examples 550
Introduction 558
Remarks 558
Examples 558
Pitfall - Leaving out braces: the "dangling if" and "dangling else" problems 561
Pitfall - Declaring classes with the same names as standard classes 564
Remarks 569
Examples 569
In summary 573
Pitfall - Not checking if an I/O stream isn't even initialized when closing it 573
Introduction 576
Remarks 576
Examples 576
Solution 576
Pitfall - Interning strings so that you can use == is a bad idea 585
Fragility 585
Examples 590
Remarks 599
Examples 599
Introduction 604
Examples 604
Introduction 609
Remarks 609
Examples 609
Introduction 612
Remarks 612
Examples 612
Introduction 614
Remarks 614
Examples 614
Examples 618
Introduction 619
Syntax 619
Remarks 619
Examples 620
Introduction 621
Syntax 621
Parameters 621
Remarks 621
Examples 621
Example 627
Adapter 627
Examples 631
Introduction 632
Examples 632
Examples 637
Syntax 641
Remarks 641
Examples 641
Expressions 642
Variables 642
Introduction 645
Remarks 645
Examples 645
Details 648
Deserialization: 648
JSONObject.NULL 650
Details 652
Note 652
Remarks 654
History 654
Examples 654
Overview 654
Remarks 657
Examples 657
-XXaggressive 657
-XXallocClearChunks 657
-XXallocClearChunkSize 658
-XXcallProfiling 658
-XXdisableFatSpin 658
-XXdisableGCHeuristics 659
-XXdumpSize 659
-XXexitOnOutOfMemory 659
Remarks 661
Examples 661
Syntax 665
Examples 665
Cheat-Sheet 672
`return` only returns from the lambda, not the outer method 674
Using lambda expressions & predicates to get a certain value(s) from a list 680
Introduction 682
Examples 682
Java LinkedHashMap class 682
Introduction 684
Examples 684
Introduction 685
Syntax 685
Remarks 685
Examples 686
Removing elements from list B that are present in the list A 691
ArrayList 696
AttributeList 696
CopyOnWriteArrayList 696
LinkedList 696
RoleList 697
RoleUnresolvedList 697
Stack 697
Vector 697
Chapter 108: Literals 699
Introduction 699
Examples 699
Underscores 705
Introduction 707
Examples 707
Remarks 708
Locale 709
Language 710
Syntax 712
Parameters 712
Remarks 712
Examples 712
Intro 714
Introduction 716
Syntax 716
Remarks 716
Examples 717
Examples 723
Introduction 727
Remarks 727
Examples 727
Introduction 739
Syntax 742
Remarks 742
Examples 742
Introduction 744
Examples 744
Example of a multi-release Jar file's contents 744
Introduction 747
Syntax 747
Remarks 747
Examples 747
Introduction 752
Syntax 752
Remarks 752
Examples 753
Constructors 758
Examples 761
Multicasting 766
Notes 770
Syntax 771
Examples 771
Examples 775
Introduction 777
Examples 777
final 777
volatile 778
static 779
abstract 780
synchronized 781
transient 782
strictfp 782
Examples 783
NumberFormat 783
Introduction 784
Syntax 784
Examples 784
Examples 798
Remarks 802
Examples 802
Introduction 806
Remarks 806
Examples 806
Syntax 814
Common Usage 815
The Assignment Operators (=, +=, -=, *=, /=, %=, <<=, >>= , >>>=, &=, |= and ^=) 818
Introduction 825
Syntax 825
Examples 825
Map 826
Filter 827
FlatMap 829
Introduction 830
Remarks 830
Examples 830
Variables 831
Type Variables 831
Constants 831
Modifiers 834
Indentation 835
Whitespace 837
Annotations 838
Literals 840
Braces 840
Introduction 842
Remarks 842
Examples 842
Examples 844
Introduction 846
Remarks 846
Examples 846
Examples 855
PreferenceChangeEvent 855
NodeChangeEvent 855
Introduction 862
Syntax 862
Remarks 862
Examples 863
Remarks 874
Examples 874
ch.vorburger.exec 876
Pitfall: Runtime.exec, Process and ProcessBuilder don't understand shell syntax 876
Introduction 879
Syntax 879
Remarks 879
Examples 880
Stacks 886
Example 886
BlockingQueue 887
Deque 889
Remarks 891
Examples 891
Introduction 896
Examples 896
BufferedReader 896
Introduction 896
Introduction 899
Remarks 899
Output 899
Examples 900
Example 903
Workaround 904
Example 904
Examples 908
Dereferencing 908
Examples 910
Introduction 912
Remarks 912
Performance 912
Examples 912
Introduction 912
Introduction 924
Syntax 924
Remarks 924
Imports 924
Pitfalls 924
Examples 925
Using regex with custom behaviour by compiling the Pattern with flags 926
Remarks 930
Examples 930
Client-Server: invoking methods in one JVM from another 930
Overview 932
Introduction 940
Remarks 940
Examples 941
Examples 945
Examples 950
Syntax 951
Parameters 951
Remarks 951
Examples 951
General Pattern that does most commonly asked about tasks 953
Syntax 956
Examples 956
Examples 958
Introduction 962
Remarks 962
Examples 962
Examples 964
Demo 972
Introduction 974
Examples 974
Remarks 985
Examples 985
Service 985
META-INF/services/servicetest.Logger 986
Usage 986
Examples 989
Introduction 994
Examples 994
Thread-safe lazy initialization using holder class | Bill Pugh Singleton implementation 996
Introduction 1000
Examples 1000
Introduction 1001
Examples 1001
Remarks 1003
Examples 1003
Introduction 1004
Examples 1004
Introduction 1007
Syntax 1007
Examples 1007
Cheat-Sheet 1012
h21 1015
Introduction 1033
Examples 1033
Introduction 1035
Examples 1035
Introduction 1037
Syntax 1037
Remarks 1037
Examples 1037
Introduction 1040
Remarks 1040
Examples 1041
Comparing Strings 1041
Substrings 1047
Regex 1057
Remarks 1061
Examples 1061
Instantiating sun.misc.Unsafe via reflection 1061
Examples 1064
Introduction 1067
Remarks 1067
Examples 1067
Syntax 1073
Remarks 1073
Examples 1073
Examples 1083
Remarks 1084
Examples 1084
Introduction 1088
Examples 1088
Syntax 1093
Examples 1093
Introduction 1096
Remarks 1096
Examples 1096
Introduction 1100
Remarks 1100
Examples 1100
Syntax 1103
Examples 1103
Introduction 1106
Examples 1106
Performing Asynchronous Tasks Where No Return Value Is Needed Using a Runnable Class Insta 1106
Performing Asynchronous Tasks Where a Return Value Is Needed Using a Callable Class Instan 1108
Remarks 1113
Examples 1113
Syntax 1115
Remarks 1115
Examples 1116
Introduction 1119
Examples 1119
Introduction 1121
Syntax 1121
Parameters 1121
Remarks 1121
Examples 1121
package-info.java 1124
Remarks 1125
Examples 1126
Remarks 1130
Examples 1130
Examples 1133
Credits 1139
About
You can share this PDF with anyone you feel could benefit from it, downloaded the latest version
from: java-language
It is an unofficial and free Java Language ebook created for educational purposes. All the content
is extracted from Stack Overflow Documentation, which is written by many hardworking individuals
at Stack Overflow. It is neither affiliated with Stack Overflow nor official Java Language.
The content is released under Creative Commons BY-SA, and the list of contributors to each
chapter are provided in the credits section at the end of this book. Images may be copyright of
their respective owners unless otherwise specified. All trademarks and registered trademarks are
the property of their respective company owners.
Use the content presented in this book at your own risk; it is not guaranteed to be correct nor
accurate, please send your feedback and corrections to [email protected]
https://riptutorial.com/ 1
Chapter 1: Getting started with Java
Language
Remarks
The Java programming language is...
• Class-based: Its object structure is defined in classes. Class instances always have those
fields and methods specified in their class definitions (see Classes and Objects). This is in
contrast to non-class-based languages such as JavaScript.
• Statically-typed: the compiler checks at compile time that variable types are respected. For
example, if a method expects an argument of type String, that argument must in fact be a
string when the method is called.
• Object-oriented: most things in a Java program are class instances, i.e. bundles of state
(fields) and behavior (methods which operate on data and form the object's interface to the
outside world).
• Portable: It can be compiled on any platform with javac and the resultant class files can run
on any platform that has a JVM.
Java is intended to let application developers "write once, run anywhere" (WORA), meaning that
compiled Java code can run on all platforms that support Java without the need for recompilation.
Java code is compiled to bytecode (the .class files) which in turn get interpreted by the Java
Virtual Machine (JVM). In theory, bytecode created by one Java compiler should run the same
way on any JVM, even on a different kind of computer. The JVM might (and in real-world
programs will) choose to compile into native machine commands the parts of the bytecode that are
executed often. This is called "Just-in-time (JIT) compilation".
• Java Standard Edition (SE) is the edition that is designed for general use.
• Java Enterprise Edition (EE) adds a range of facilities for building "enterprise grade" services
in Java. Java EE is covered separately.
• Java Micro Edition (ME) is based on a subset of Java SE and is intended for use on small
devices with limited resources.
https://riptutorial.com/ 2
Each edition has multiple versions. The Java SE versions are listed below.
Installing Java
There is a separate topic on Installing Java (Standard Edition).
What's next?
Here are links to subjects to continue learning and understanding the Java programming
language. These subjects are the basics of the Java programming to get you started.
Testing
While Java does not have any support for testing in the standard library, there are 3rd-party
libraries that are designed to support testing. The two most popular unit testing libraries are:
Other
• Design patterns for Java are covered in Design Patterns.
• Programming for Android is covered in Android.
• Java Enterprise Edition technologies are covered in Java EE.
• The Oracle JavaFX technologies are covered in JavaFX.
https://riptutorial.com/ 3
1. In Versions section the end-of-life (free) date is when Oracle will stop posting further updates of Java SE to its
public download sites. Customers who need continued access to critical bug fixes and security fixes as well as general
maintenance for Java SE can get long term support through Oracle Java SE Support.
Versions
Examples
Creating Your First Java Program
Create a new file in your text editor or IDE named HelloWorld.java. Then paste this code block into
the file and save:
Note: For Java to recognize this as a public class (and not throw a compile time error), the
filename must be the same as the class name (HelloWorld in this example) with a .java extension.
There should also be a public access modifier before it.
Naming conventions recommend that Java classes begin with an uppercase character, and be in
camel case format (in which the first letter of each word is capitalized). The conventions
https://riptutorial.com/ 4
recommend against underscores (_) and dollar signs ($).
cd /path/to/containing/folder/
$ javac HelloWorld.java
It's fairly common to get the error 'javac' is not recognized as an internal or external command,
operable program or batch file. even when you have installed the JDK and are able to run the
program from IDE ex. eclipse etc. Since the path is not added to the environment by default.
In case you get this on windows, to resolve, first try browsing to your javac.exe path, it's most
probably in your C:\Program Files\Java\jdk(version number)\bin. Then try running it with below.
Previously when we were calling javac it was same as above command. Only in that case your OS
knew where javac resided. So let's tell it now, this way you don't have to type the whole path
every-time. We would need to add this to our PATH
You cannot undo this so be careful. First copy your existing path to notepad. Then to get the
exact PATH to your javac browse manually to the folder where javac resides and click on the
address bar and then copy it. It should look something like c:\Program Files\Java\jdk1.8.0_xx\bin
In "Variable value" field, paste this IN FRONT of all the existing directories, followed by a semi-
colon (;). DO NOT DELETE any existing entries.
The compiler will then generate a bytecode file called HelloWorld.class which can be executed in
the Java Virtual Machine (JVM). The Java programming language compiler, javac, reads source
https://riptutorial.com/ 5
files written in the Java programming language and compiles them into bytecode class files.
Optionally, the compiler can also process annotations found in source and class files using the
Pluggable Annotation Processing API. The compiler is a command line tool but can also be invoked
using the Java Compiler API.
To run your program, enter java followed by the name of the class which contains the main method
(HelloWorld in our example). Note how the .class is omitted:
$ java HelloWorld
Hello, World!
You have successfully coded and built your very first Java program!
Note: In order for Java commands (java, javac, etc) to be recognized, you will need to make sure:
You will need to use a compiler (javac) and an executor (java) provided by your JVM. To find out
which versions you have installed, enter java -version and javac -version on the command line.
The version number of your program will be printed in the terminal (e.g. 1.8.0_73).
The class keyword begins the class definition for a class named HelloWorld. Every Java application
contains at least one class definition (Further information about classes).
This is an entry point method (defined by its name and signature of public static void
main(String[])) from which the JVM can run your program. Every Java program should have one. It
is:
• public:
meaning that the method can be called from anywhere mean from outside the
program as well. See Visibility for more information on this.
• static: meaning it exists and can be run by itself (at the class level without creating an
https://riptutorial.com/ 6
object).
• void: meaning it returns no value. Note: This is unlike C and C++ where a return code such
as int is expected (Java's way is System.exit()).
• An array (typically called args) of Strings passed as arguments to main function (e.g. from
command line arguments).
Non-required parts:
• The name args is a variable name, so it can be called anything you want, although it is
typically called args.
• Whether its parameter type is an array (String[] args) or Varargs (String... args) does not
matter because arrays can be passed into varargs.
Note: A single application may have multiple classes containing an entry point (main) method. The
entry point of the application is determined by the class name passed as an argument to the java
command.
System.out.println("Hello, World!");
Element Purpose
this denotes that the subsequent expression will call upon the System class, from
System
the java.lang package.
this is a "dot operator". Dot operators provide you access to a classes members
. 1; i.e. its fields (variables) and its methods. In this case, this dot operator allows
you to reference the out static field within the System class.
this is the name of the static field of PrintStream type within the System class
out
containing the standard output functionality.
this is another dot operator. This dot operator provides access to the println
.
method within the out variable.
this is the name of a method within the PrintStream class. This method in
println particular prints the contents of the parameters into the console and inserts a
newline after.
this parenthesis indicates that a method is being accessed (and not a field) and
(
begins the parameters being passed into the println method.
https://riptutorial.com/ 7
Element Purpose
"Hello, this is the String literal that is passed as a parameter, into the println method.
World!" The double quotation marks on each end delimit the text as a String.
this parenthesis signifies the closure of the parameters being passed into the
)
println method.
Here's another example demonstrating the OO paradigm. Let's model a football team with one
(yes, one!) member. There can be more, but we'll discuss that when we get to arrays.
class Member {
private String name;
private String type;
private int level; // note the data type here
private int rank; // note the data type here as well
Why do we use private here? Well, if someone wanted to know your name, they should ask you
directly, instead of reaching into your pocket and pulling out your Social Security card. This private
does something like that: it prevents outside entities from accessing your variables. You can only
return private members through getter functions (shown below).
After putting it all together, and adding the getters and main method as discussed before, we
have:
https://riptutorial.com/ 8
public class Team {
Member member;
public Team(Member member) {
this.member = member;
}
class Member {
private String name;
private String type;
private int level;
private int rank;
Output:
Aurieel
light
10
1
Run on ideone
Once again, the main method inside the Test class is the entry point to our program. Without the
main method, we cannot tell the Java Virtual Machine (JVM) from where to begin execution of the
https://riptutorial.com/ 9
program.
1 - Because the HelloWorld class has little relation to the System class, it can only access public data.
https://riptutorial.com/ 10
Chapter 2: 2D Graphics in Java
Introduction
Graphics are visual images or designs on some surface, such as a wall, canvas, screen, paper, or
stone to inform, illustrate, or entertain. It includes: pictorial representation of data, as in computer-
aided design and manufacture, in typesetting and the graphic arts, and in educational and
recreational software. Images that are generated by a computer are called computer graphics.
The Java 2D API is powerful and complex. There are multiple ways to do 2D graphics in Java.
Examples
Example 1: Draw and Fill a Rectangle Using Java
This is an Example which print rectangle and fill color in the rectangle.
https://i.stack.imgur.com/dlC5v.jpg
Most methods of the Graphics class can be divided into two basic groups:
1. Draw and fill methods, enabling you to render basic shapes, text, and images
2. Attributes setting methods, which affect how that drawing and filling appears
Code Example: Let us start this with a little example of drawing a rectangle and filling color in it.
There we declare two classes, one class is MyPanel and other Class is Test. In class MyPanel we
use drawRect( ) & fillRect( ) mathods to draw rectangle and fill Color in it. We set the color by
setColor(Color.blue) method. In Second Class we Test our graphic which is Test Class we make a
https://riptutorial.com/ 11
Frame and put MyPanel with p=new MyPanel() object in it.By running Test Class we see a
Rectangle and a Blue Color Filled Rectangle.
import javax.swing.*;
import java.awt.*;
// MyPanel extends JPanel, which will eventually be placed in a JFrame
public class MyPanel extends JPanel {
// custom painting is performed by the paintComponent method
@Override
public void paintComponent(Graphics g){
// clear the previous painting
super.paintComponent(g);
// cast Graphics to Graphics2D
Graphics2D g2 = (Graphics2D) g;
g2.setColor(Color.red); // sets Graphics2D color
// draw the rectangle
g2.drawRect(0,0,100,100); // drawRect(x-position, y-position, width, height)
g2.setColor(Color.blue);
g2.fillRect(200,0,100,100); // fill new rectangle with color blue
}
}
import javax.swing.;
import java.awt.;
public class Test { //the Class by which we display our rectangle
JFrame f;
MyPanel p;
public Test(){
f = new JFrame();
// get the content area of Panel.
Container c = f.getContentPane();
// set the LayoutManager
c.setLayout(new BorderLayout());
p = new MyPanel();
// add MyPanel object into container
c.add(p);
// set the size of the JFrame
f.setSize(400,400);
// make the JFrame visible
f.setVisible(true);
// sets close behavior; EXIT_ON_CLOSE invokes System.exit(0) on closing the JFrame
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
paintComponent( )
https://riptutorial.com/ 12
• It is a main method for painting
• By default, it first paints the background
• After that, it performs custom painting (drawing circle, rectangles etc.)
Note: The Java 2D API enables you to easily perform the following tasks:
import javax.swing.*;
import java.awt.*;
g2.fillOval(int x,int y,int height, int width); This method will fill an oval at specified x and y
position with given height and width.
https://riptutorial.com/ 13
Chapter 3: Alternative Collections
Remarks
This topic about Java collections from guava, apache, eclipse: Multiset, Bag, Multimap, utils
function from this lib and so on.
Examples
Apache HashBag, Guava HashMultiset and Eclipse HashBag
A Bag/ultiset stores each object in the collection together with a count of occurrences. Extra
methods on the interface allow multiple copies of an object to be added or removed at once. JDK
analog is HashMap<T, Integer>, when values is count of copies this key.
Apache Commons
Type Guava GS Collections JDK
Collections
Order not
HashMultiset HashBag HashBag HashMap
defined
Insertion-
LinkedHashMultiset - - LinkedHa
order
Concurrent
ConcurrentHashMultiset SynchronizedBag SynchronizedBag Collection
variant
Concurrent
- SynchronizedSortedBag SynchronizedSortedBag Collection
and sorted
Immutable
ImmutableMultiset UnmodifiableBag UnmodifiableBag Collection
collection
Immutable Collection
ImmutableSortedMultiset UnmodifiableSortedBag UnmodifiableSortedBag )
and sorted
Examples:
https://riptutorial.com/ 14
TreeBag(Arrays.asList(INPUT_TEXT.split(" "))));
https://riptutorial.com/ 15
// Print count words
System.out.println(multiset); // print [Hello x 2, World! x 2, All!, Hi]- in predictable
iteration order
// Print all unique words
System.out.println(multiset.elementSet()); // print [Hello, World!, All!, Hi] - in
predictable iteration order
More examples:
I. Apache Collection:
III. Guava
This multimap allows duplicate key-value pairs. JDK analogs are HashMap<K, List>, HashMap<K,
Set> and so on.
Key's Value's
Duplicate Analog key Analog value Guava Apache
order order
not Insertion-
yes HashMap ArrayList ArrayListMultimap MultiVal
defined order
https://riptutorial.com/ 16
Key's Value's
Duplicate Analog key Analog value Guava Apache
order order
MultiVal
not not multiVal
no HashMap HashSet HashMultimap HashMap<
defined defined
HashSet.
Multimaps.
not MultiVal
newMultimap(
sorted no HashMap TreeSet HashMap, Supplier
new Hash
defined TreeSet.
<TreeSet>)
MultiVal
Insertion- Insertion- multiVal
yes LinkedHashMap ArrayList LinkedListMultimap
order order LinkedH
ArrayLis
MultiVal
Insertion- Insertion- multiVal
no LinkedHashMap LinkedHashSet LinkedHashMultimap LinkedHa
order order
LinkedHa
MultiVal
multiVal
sorted sorted no TreeMap TreeSet TreeMultimap TreeMap<
Set>(),T
Task: Parse "Hello World! Hello All! Hi World!" string to separate words and print all indexes of
every word using MultiMap (for example, Hello=[0, 2], World!=[1, 5] and so on)
// Fill Multimap
int i = 0;
for(String word: words) {
multiMap.put(word, i);
i++;
}
https://riptutorial.com/ 17
System.out.println("Hi = " + multiMap.get("Hi")); // print [4]
System.out.println("Empty = " + multiMap.get("Empty")); // print null
// Create Multiset
MutableBiMap<String, String> biMap = new HashBiMap(englishWords.length);
// Create English-Polish dictionary
int i = 0;
for(String englishWord: englishWords) {
biMap.put(englishWord, russianWords[i]);
i++;
}
// Fill Multimap
int i = 0;
for(String word: words) {
multiMap.put(word, i);
i++;
}
https://riptutorial.com/ 18
System.out.println(multiMap.keySet()); // print [Hi, Hello, World!, All!] - in random
orders
Nore examples:
I. Apache Collection:
1. MultiValueMap
2. MultiValueMapLinked
3. MultiValueMapTree
1. FastListMultimap
2. HashBagMultimap
3. TreeSortedSetMultimap
4. UnifiedSetMultimap
III. Guava
1. HashMultiMap
2. LinkedHashMultimap
3. LinkedListMultimap
4. TreeMultimap
5. ArrayListMultimap
1. Create List
Description JDK guava gs-collections
Create
new ArrayList<>() Lists.newArrayList() FastList.newList()
empty list
https://riptutorial.com/ 19
Description JDK guava gs-collections
from values
Create list
with
new ArrayList<>(100) Lists.newArrayListWithCapacity(100) FastList.newList(100)
capacity =
100
Create list
new
from any ArrayList<>(collection)
Lists.newArrayList(collection) FastList.newList(collecti
collectin
Create list
from any - Lists.newArrayList(iterable) FastList.newList(iterable
Iterable
Create list
- Lists.newArrayList(iterator) -
from Iterator
Create list
Arrays.asList(array) Lists.newArrayList(array) FastList.newListWith(arra
from array
Create list
FastList.newWithNValues(1
using - - () -> "1")
factory
Examples:
System.out.println("createArrayList start");
// Create empty list
List<String> emptyGuava = Lists.newArrayList(); // using guava
List<String> emptyJDK = new ArrayList<>(); // using JDK
MutableList<String> emptyGS = FastList.newList(); // using gs
System.out.println(withElements);
System.out.println(withElementsJDK);
System.out.println(withElementsGS);
https://riptutorial.com/ 20
// Create list from any Iterable interface (any collection)
Collection<String> collection = new HashSet<>(3);
collection.add("1");
collection.add("2");
collection.add("3");
System.out.println(fromIterable);
System.out.println(fromIterableJDK);
System.out.println(fromIterableGS);
/* Attention: JDK create list only from Collection, but guava and gs can create list from
Iterable and Collection */
System.out.println("createArrayList end");
2 Create Set
Description JDK guava gs-collections
Create
new HashSet<>() Sets.newHashSet() UnifiedSet.newSet()
empty set
new
Creatre set HashSet<>(Arrays.asList("alpha", Sets.newHashSet("alpha", UnifiedSet.newSetWith("a
from values "beta", "gamma") "beta", "gamma")
"beta", "gamma"))
Create set
from any new HashSet<>(collection) Sets.newHashSet(collection) UnifiedSet.newSet(collec
collections
Create set
from any - Sets.newHashSet(iterable) UnifiedSet.newSet(iterab
Iterable
https://riptutorial.com/ 21
Description JDK guava gs-collections
from any
Iterator
Examples:
System.out.println("createHashSet start");
// Create empty set
Set<String> emptyGuava = Sets.newHashSet(); // using guava
Set<String> emptyJDK = new HashSet<>(); // using JDK
Set<String> emptyGS = UnifiedSet.newSet(); // using gs
System.out.println(withElements);
System.out.println(withElementsJDK);
System.out.println(withElementsGS);
System.out.println(fromIterable);
System.out.println(fromIterableJDK);
System.out.println(fromIterableGS);
/* Attention: JDK create set only from Collection, but guava and gs can create set from
Iterable and Collection */
https://riptutorial.com/ 22
System.out.println(fromArrayGS);
System.out.println("createHashSet end");
3 Create Map
Description JDK guava gs-collections
Create new
Maps.newHashMap() UnifiedMap.newMap()
empty map HashMap<>()
Create map
with new
Maps.newHashMapWithExpectedSize(100) UnifiedMap.newMap(130)
capacity = HashMap<>(130)
130
Create map
new
from other HashMap<>(map)
Maps.newHashMap(map) UnifiedMap.newMap(map)
map
Examples:
System.out.println("createHashMap start");
// Create empty map
Map<String, String> emptyGuava = Maps.newHashMap(); // using guava
Map<String, String> emptyJDK = new HashMap<>(); // using JDK
Map<String, String> emptyGS = UnifiedMap.newMap(); // using gs
System.out.println(withMap);
System.out.println(withMapJDK);
System.out.println(withMapGS);
System.out.println("createHashMap end");
https://riptutorial.com/ 23
1. CollectionCompare
2. CollectionSearch
3. JavaTransform
https://riptutorial.com/ 24
Chapter 4: Annotations
Introduction
In Java, an annotation is a form of syntactic metadata that can be added to Java source code. It
provides data about a program that is not part of the program itself. Annotations have no direct
effect on the operation of the code they annotate. Classes, methods, variables, parameters and
packages are allowed to be annotated.
Syntax
• @AnnotationName // 'Marker annotation' (no parameters)
• @AnnotationName(someValue) // sets parameter with the name 'value'
• @AnnotationName(param1 = value1) // named parameter
• @AnnotationName(param1 = value1, param2 = value2) // multiple named parameters
• @AnnotationName(param1 = {1, 2, 3}) // named array parameter
• @AnnotationName({value1}) // array with single element as parameter with the name 'value'
Remarks
Parameter types
Only constant expressions of following types are allowed for parameters, as well as arrays of
these types:
• String
• Class
• primitive types
• Enum types
• Annotation Types
Examples
Built-in annotations
The Standard Edition of Java comes with some annotations predefined. You do not need to define
them by yourself and you can use them immediately. They allow the compiler to enable some
fundamental checking of methods, classes and code.
@Override
This annotation applies to a method and says that this method must override a superclass' method
or implement an abstract superclass' method definition. If this annotation is used with any other
https://riptutorial.com/ 25
kind of method, the compiler will throw an error.
Concrete superclass
Abstract class
class Logger1 {
public void log(String logString) {
System.out.prinln(logString);
}
}
class Logger2 {
// This will throw compile-time error. Logger2 is not a subclass of Logger1.
// log method is not overriding anything
@Override
public void log(String logString) {
System.out.println("Log 2" + logString);
}
}
The main purpose is to catch mistyping, where you think you are overriding a method, but are
actually defining a new one.
class Vehicle {
public void drive() {
System.out.println("I am driving");
}
https://riptutorial.com/ 26
}
• In Java 5, it meant that the annotated method had to override a non-abstract method
declared in the superclass chain.
• From Java 6 onward, it is also satisfied if the annotated method implements an abstract
method declared in the classes superclass / interface hierarchy.
(This can occasionally cause problems when back-porting code to Java 5.)
@Deprecated
This marks the method as deprecated. There can be several reasons for this:
The specific reason for deprecation can usually be found in the documentation of the API.
The annotation will cause the compiler to emit an error if you use it. IDEs may also highlight this
method somehow as deprecated
class ComplexAlgorithm {
@Deprecated
public void oldSlowUnthreadSafeMethod() {
// stuff here
}
@SuppressWarnings
https://riptutorial.com/ 27
In almost all cases, when the compiler emits a warning, the most appropriate action is to fix the
cause. In some instances (Generics code using untype-safe pre-generics code, for example) this
may not be possible and it's better to suppress those warnings that you expect and cannot fix, so
you can more clearly see unexpected warnings.
This annotation can be applied to a whole class, method or line. It takes the category of warning
as a parameter.
@SuppressWarnings("deprecation")
public class RiddledWithWarnings {
// several methods calling deprecated code here
}
@SuppressWarning("finally")
public boolean checkData() {
// method calling return from within finally block
}
It is better to limit the scope of the annotation as much as possible, to prevent unexpected
warnings also being suppressed. For example, confining the scope of the annotation to a single-
line:
The warnings supported by this annotation may vary from compiler to compiler. Only the unchecked
and deprecation warnings are specifically mentioned in the JLS. Unrecognized warning types will
be ignored.
@SafeVarargs
Because of type erasure, void method(T... t) will be converted to void method(Object[] t) meaning
that the compiler is not always able to verify that the use of varargs is type-safe. For instance:
There are instances where the use is safe, in which case you can annotate the method with the
SafeVarargs annotation to suppress the warning. This obviously hides the warning if your use is
unsafe too.
@FunctionalInterface
This is an optional annotation used to mark a FunctionalInterface. It will cause the compiler to
complain if it does not conform to the FunctionalInterface spec (has a single abstract method)
@FunctionalInterface
public interface ITrade {
https://riptutorial.com/ 28
public boolean check(Trade t);
}
@FunctionalInterface
public interface Predicate<T> {
boolean test(T t);
}
Java's Reflection API allows the programmer to perform various checks and operations on class
fields, methods and annotations during runtime. However, in order for an annotation to be at all
visible at runtime, the RetentionPolicy must be changed to RUNTIME, as demonstrated in the
example below:
@interface MyDefaultAnnotation {
@Retention(RetentionPolicy.RUNTIME)
@interface MyRuntimeVisibleAnnotation {
@MyDefaultAnnotation
static class RuntimeCheck1 {
}
@MyRuntimeVisibleAnnotation
static class RuntimeCheck2 {
}
Annotation types are defined with @interface. Parameters are defined similar to methods of a
regular interface.
@interface MyAnnotation {
String param1();
boolean param2();
int[] param3(); // array parameter
}
https://riptutorial.com/ 29
Default values
@interface MyAnnotation {
String param1() default "someValue";
boolean param2() default true;
int[] param3() default {};
}
Meta-Annotations
Meta-annotations are annotations that can be applied to annotation types. Special predefined
meta-annotation define how annotation types can be used.
@Target
The @Target meta-annotation restricts the types the annotation can be applied to.
@Target(ElementType.METHOD)
@interface MyAnnotation {
// this annotation can only be applied to methods
}
Available Values
@Retention(RetentionPolicy.RUNTIME)
ANNOTATION_TYPE annotation types @interface MyAnnotation
@MyAnnotation
CONSTRUCTOR constructors public MyClass() {}
@XmlAttribute
FIELD fields, enum constants private int count;
https://riptutorial.com/ 30
ElementType target example usage on target element
@XmlElement
METHOD methods public int getCount() {...}
public Rectangle(
@NamedArg("width") double
width,
method/constructor
PARAMETER @NamedArg("height") double
parameters height) {
...
}
Java SE 8
ElementType target example usage on target element
Object o = "42";
TYPE_USE Use of a type String s = (@MyAnnotation String) o;
@Retention
The @Retention meta-annotation defines the annotation visibility during the applications compilation
process or execution. By default, annotations are included in .class files, but are not visible at
runtime. To make an annotation accessible at runtime, RetentionPolicy.RUNTIME has to be set on
that annotation.
@Retention(RetentionPolicy.RUNTIME)
@interface MyAnnotation {
https://riptutorial.com/ 31
// this annotation can be accessed with reflections at runtime
}
Available values
RetentionPolicy Effect
CLASS The annotation is available in the .class file, but not at runtime
RUNTIME The annotation is available at runtime and can be accessed via reflection
The annotation is available at compile time, but not added to the .class
SOURCE
files. The annotation can be used e.g. by an annotation processor.
@Documented
The @Documented meta-annotation is used to mark annotations whose usage should be documented
by API documentation generators like javadoc. It has no values. With @Documented, all classes that
use the annotation will list it on their generated documentation page. Without @Documented, it's not
possible to see which classes use the annotation in the documentation.
@Inherited
The @Inherited meta-annotation is relevant to annotations that are applied to classes. It has no
values. Marking an annotation as @Inherited alters the way that annotation querying works.
• For a non-inherited annotation, the query only examines the class being examined.
• For an inherited annotation, the query will also check the super-class chain (recursively) until
an instance of the annotation is found.
Note that only the super-classes are queried: any annotations attached to interfaces in the classes
hierarchy will be ignored.
@Repeatable
The @Repeatable meta-annotation was added in Java 8. It indicates that multiple instances of the
annotation can be attached to the annotation's target. This meta-annotation has no values.
You can fetch the current properties of the Annotation by using Reflection to fetch the Method or
Field or Class which has an Annotation applied to it, and then fetching the desired properties.
@Retention(RetentionPolicy.RUNTIME)
@interface MyAnnotation {
String key() default "foo";
https://riptutorial.com/ 32
String value() default "bar";
}
class AnnotationExample {
// Put the Annotation on the method, but leave the defaults
@MyAnnotation
public void testDefaults() throws Exception {
// Using reflection, get the public method "testDefaults", which is this method with
no args
Method method = AnnotationExample.class.getMethod("testDefaults", null);
foo = bar
baz = buzz
Repeating Annotations
https://riptutorial.com/ 33
Until Java 8, two instances of the same annotation could not be applied to a single element. The
standard workaround was to use a container annotation holding an array of some other
annotation:
// Author.java
@Retention(RetentionPolicy.RUNTIME)
public @interface Author {
String value();
}
// Authors.java
@Retention(RetentionPolicy.RUNTIME)
public @interface Authors {
Author[] value();
}
// Test.java
@Authors({
@Author("Mary"),
@Author("Sam")
})
public class Test {
public static void main(String[] args) {
Author[] authors = Test.class.getAnnotation(Authors.class).value();
for (Author author : authors) {
System.out.println(author.value());
// Output:
// Mary
// Sam
}
}
}
Java SE 8
Java 8 provides a cleaner, more transparent way of using container annotations, using the
@Repeatable annotation. First we add this to the Author class:
@Repeatable(Authors.class)
This tells Java to treat multiple @Author annotations as though they were surrounded by the
@Authors container. We can also use Class.getAnnotationsByType() to access the @Author array by its
own class, instead of through its container:
@Author("Mary")
@Author("Sam")
public class Test {
public static void main(String[] args) {
Author[] authors = Test.class.getAnnotationsByType(Author.class);
for (Author author : authors) {
System.out.println(author.value());
// Output:
// Mary
// Sam
}
}
https://riptutorial.com/ 34
}
Inherited Annotations
By default class annotations do not apply to types extending them. This can be changed by adding
the @Inherited annotation to the annotation definition
Example
Consider the following 2 Annotations:
@Inherited
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
public @interface InheritedAnnotationType {
}
and
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
public @interface UninheritedAnnotationType {
}
@UninheritedAnnotationType
class A {
}
@InheritedAnnotationType
class B extends A {
}
class C extends B {
}
System.out.println(new A().getClass().getAnnotation(InheritedAnnotationType.class));
System.out.println(new B().getClass().getAnnotation(InheritedAnnotationType.class));
System.out.println(new C().getClass().getAnnotation(InheritedAnnotationType.class));
System.out.println("_________________________________");
System.out.println(new A().getClass().getAnnotation(UninheritedAnnotationType.class));
System.out.println(new B().getClass().getAnnotation(UninheritedAnnotationType.class));
System.out.println(new C().getClass().getAnnotation(UninheritedAnnotationType.class));
will print a result similar to this (depending on the packages of the annotation):
null
@InheritedAnnotationType()
@InheritedAnnotationType()
https://riptutorial.com/ 35
_________________________________
@UninheritedAnnotationType()
null
null
Note that annotations can only be inherited from classes, not interfaces.
The annotation
The @Setter annotation is a marker can be applied to methods. The annotation will be discarded
during compilation not be available afterwards.
package annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Retention(RetentionPolicy.SOURCE)
@Target(ElementType.METHOD)
public @interface Setter {
}
package annotation.processor;
import annotation.Setter;
import java.util.Set;
import javax.annotation.processing.AbstractProcessor;
import javax.annotation.processing.Messager;
import javax.annotation.processing.ProcessingEnvironment;
import javax.annotation.processing.RoundEnvironment;
import javax.annotation.processing.SupportedAnnotationTypes;
import javax.annotation.processing.SupportedSourceVersion;
import javax.lang.model.SourceVersion;
import javax.lang.model.element.Element;
import javax.lang.model.element.ElementKind;
https://riptutorial.com/ 36
import javax.lang.model.element.ExecutableElement;
import javax.lang.model.element.Modifier;
import javax.lang.model.element.TypeElement;
import javax.tools.Diagnostic;
@SupportedAnnotationTypes({"annotation.Setter"})
@SupportedSourceVersion(SourceVersion.RELEASE_8)
public class SetterProcessor extends AbstractProcessor {
@Override
public boolean process(Set<? extends TypeElement> annotations, RoundEnvironment roundEnv)
{
// get elements annotated with the @Setter annotation
Set<? extends Element> annotatedElements =
roundEnv.getElementsAnnotatedWith(Setter.class);
@Override
public void init(ProcessingEnvironment processingEnvironment) {
super.init(processingEnvironment);
https://riptutorial.com/ 37
// get messager for printing errors
messager = processingEnvironment.getMessager();
}
Packaging
To be applied by the compiler, the annotation processor needs to be made available to the SPI
(see ServiceLoader).
annotation.processor.SetterProcessor
import annotation.Setter;
@Setter
private void setValue(String value) {}
@Setter
public void setString(String value) {}
@Setter
public static void main(String[] args) {}
https://riptutorial.com/ 38
yields the following output
This could be prevented by specifying the -proc:none option for javac. You could also forgo the
usual compilation by specifying -proc:only instead.
IDE integration
Netbeans
Annotation processors can be used in the NetBeans editor. To do this the annotation processor
needs to be specified in the project settings:
2. add check marks for Enable Annotation Processing and Enable Annotation Processing in
Editor
4. in the popup that appears enter the fully qualified class name of the annotation processor
and click Ok.
Result
https://riptutorial.com/ 39
The idea behind Annotations
Annotations may appear before types or declarations. It is possible for them to appear in a place
where they could apply to both a type or a declaration.
What exactly an annotation applies to is governed by the "meta-annotation" @Target. See "Defining
annotation types" for more information.
Annotations are used for a multitude of purposes. Frameworks like Spring and Spring-MVC make
use of annotations to define where Dependencies should be injected or where requests should be
routed.
Other frameworks use annotations for code-generation. Lombok and JPA are prime examples,
that use annotations to generate Java (and SQL) code.
When Java annotations were first introduced there was no provision for annotating the target of an
instance method or the hidden constructor parameter for an inner classes constructor. This was
remedied in Java 8 with addition of receiver parameter declarations; see JLS 8.4.1.
The following example illustrates the syntax for both kinds of receiver parameter:
https://riptutorial.com/ 40
// ...
}
public void doIt(Inner this) {
// ...
}
}
}
The sole purpose of receiver parameters is to allow you to add annotations. For example, you
might have a custom annotation @IsOpen whose purpose is to assert that a Closeable object has not
been closed when a method is called. For example:
At one level, the @IsOpen annotation on this could simply serve as documentation. However, we
could potentially do more. For example:
• An annotation processor could insert a runtime check that this is not in closed state when
update is called.
• A code checker could perform a static code analysis to find cases where this could be
closed when update is called.
An Annotation parameter can accept multiple values if it is defined as an array. For example the
standard annotation @SuppressWarnings is defined like this:
The value parameter is an array of Strings. You can set multiple values by using a notation similar
to Array initializers:
@SuppressWarnings({"unused"})
@SuppressWarnings({"unused", "javadoc"})
If you only need to set a single value, the brackets can be omitted:
@SuppressWarnings("unused")
https://riptutorial.com/ 41
Chapter 5: Apache Commons Lang
Examples
Implement equals() method
To implement the equals method of an object easily you could use the EqualsBuilder class.
@Override
public boolean equals(Object obj) {
return builder.isEquals();
}
Using reflection:
@Override
public boolean equals(Object obj) {
return EqualsBuilder.reflectionEquals(this, obj, false);
}
the boolean parameter is to indicates if the equals should check transient fields.
@Override
public boolean equals(Object obj) {
return EqualsBuilder.reflectionEquals(this, obj, "field1", "field2");
}
To implement the hashCode method of an object easily you could use the HashCodeBuilder class.
@Override
public int hashCode() {
https://riptutorial.com/ 42
HashCodeBuilder builder = new HashCodeBuilder();
builder.append(field1);
builder.append(field2);
builder.append(field3);
return builder.hashCode();
}
Using reflection:
@Override
public int hashCode() {
return HashCodeBuilder.reflectionHashCode(this, false);
}
@Override
public int hashCode() {
return HashCodeBuilder.reflectionHashCode(this, "field1", "field2");
}
To implement the toString method of an object easily you could use the ToStringBuilder class.
@Override
public String toString() {
return builder.toString();
}
Example result:
ar.com.jonat.lang.MyClass@dd7123[<null>,0,false]
@Override
public String toString() {
https://riptutorial.com/ 43
builder.append("field2",field2);
builder.append("field3",field3);
return builder.toString();
}
Example result:
ar.com.jonat.lang.MyClass@dd7404[field1=<null>,field2=0,field3=false]
@Override
public String toString() {
return builder.toString();
}
Example result:
ar.com.bna.lang.MyClass@ebbf5c[
field1=<null>
field2=0
field3=false
]
There are some styles, for example JSON, no Classname, short, etc ...
Via reflection:
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this);
}
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this, ToStringStyle.JSON_STYLE);
}
https://riptutorial.com/ 44
Chapter 6: AppDynamics and TIBCO
BusinessWorks Instrumentation for Easy
Integration
Introduction
As AppDynamics aims to provide a way to measure application performance, speed of
development, delivery (deployment) of applications is an essential factor in making DevOps efforts
a true success. Monitoring a TIBCO BW application with AppD is generally simple and not time
consuming but when deploying large sets of applications rapid instrumentation is key. This guide
shows how to instrument all of your BW applications in a single step without modifying each
application before deploying.
Examples
Example of Instrumentation of all BW Applications in a Single Step for
Appdynamics
4. Go to the end of the file and add (replace ? with your own values as needed or remove the
flag that does not apply): java.extended.properties=-
javaagent:/opt/appd/current/appagent/javaagent.jar -Dappdynamics.http.proxyHost=? -
Dappdynamics.http.proxyPort=? -Dappdynamics.agent.applicationName=? -
Dappdynamics.agent.tierName=? -Dappdynamics.agent.nodeName=%tibco.deployment% -
Dappdynamics.controller.ssl.enabled=? -Dappdynamics.controller.sslPort=? -
Dappdynamics.agent.logs.dir=? -Dappdynamics.agent.runtime.dir=? -
Dappdynamics.controller.hostName=? -Dappdynamics.controller.port=? -
Dappdynamics.agent.accountName=? -Dappdynamics.agent.accountAccessKey=?
5. Save file and redeploy. All your applications should now be instrumented automatically at
deployment time.
Read AppDynamics and TIBCO BusinessWorks Instrumentation for Easy Integration online:
https://riptutorial.com/java/topic/10602/appdynamics-and-tibco-businessworks-instrumentation-for-
https://riptutorial.com/ 45
easy-integration
https://riptutorial.com/ 46
Chapter 7: Applets
Introduction
Applets have been part of Java since its official release and have been used to teach Java and
programming for a number of years.
Recent years have seen an active push to move away from Applets and other browser plugins,
with some browsers blocking them or actively not supporting them.
In 2016, Oracle announced their plans to deprecate the plugin, Moving to a Plugin-Free Web
Remarks
An applet is a Java application that normally runs inside a web browser. The basic idea is to
interact with the user without the need to interact with the server and transfer information. This
concept was very successful around the year 2000 when internet communication was slow and
expensive.
destroy() is called once when the applet gets removed from memory
Examples
Minimal Applet
A very simple applet draws a rectangle and prints a string something on the screen.
@Override
https://riptutorial.com/ 47
public void init() {
setBackground(Color.gray);
}
@Override
public void destroy() {}
@Override
public void start() {}
@Override
public void stop() {}
@Override
public void paint(Graphics g) {
g.setColor(Color.yellow);
g.fillRect(1,1,300,150);
g.setColor(Color.red);
g.setFont(new Font("TimesRoman", Font.PLAIN, 48));
g.drawString(str, 10, 80);
}
}
Java SE 1.2
Before Java 1.2 and the introduction of the swing API applets had extended from
java.applet.Applet.
Applets don't require a main method. The entry point is controlled by the life cycle. To use them,
they need to be embedded in a HTML document. This is also the point where their size is defined.
<html>
<head></head>
<body>
<applet code="MyApplet.class" width="400" height="200"></applet>
</body>
</html>
Creating a GUI
Applets could easily be used to create a GUI. They act like a Container and have an add() method
that takes any awt or swing component.
@Override
public void init(){
panel = new JPanel();
button = new JButton("ClickMe!");
button.addActionListener(new ActionListener(){
@Override
public void actionPerformed(ActionEvent ae) {
if(((String)cmbBox.getSelectedItem()).equals("greet")) {
https://riptutorial.com/ 48
JOptionPane.showMessageDialog(null,"Hello " + textField.getText());
} else {
JOptionPane.showMessageDialog(null,textField.getText() + " stinks!");
}
}
});
cmbBox = new JComboBox<>(new String[]{"greet", "offend"});
textField = new JTextField("John Doe");
panel.add(cmbBox);
panel.add(textField);
panel.add(button);
add(panel);
}
}
You can use the method getAppletContext() to get an AppletContext object that allows you to
request the browser to open a link. For this you use the method showDocument(). Its second
parameter tells the browser to use a new window _blank or the one that shows the applet _self.
Java applets are able to load different resources. But since they are running in the web browser of
the client you need to make sure that these resources are accessible. Applets are not able to
access client resources as the local file system.
If you want to load resources from the same URL the Applet is stored you can use the method
getCodeBase() to retrieve the base URL. To load resources, applets offer the methods getImage()
and getAudioClip() to load images or audio files.
https://riptutorial.com/ 49
public class MyImgApplet extends JApplet{
@Override
public void init(){
try {
img = getImage(new URL("http://cdn.sstatic.net/stackexchange/img/logos/so/so-
logo.png"));
} catch (MalformedURLException e) { /* omitted for brevity */ }
}
@Override
public void paint(Graphics g) {
g.drawImage(img, 0, 0, this);
}
}
@Override
public void init(){
try {
audioClip = getAudioClip(new URL("URL/TO/AN/AUDIO/FILE.WAV"));
} catch (MalformedURLException e) { /* omitted for brevity */ }
}
@Override
public void start() {
audioClip.play();
}
@Override
public void stop(){
audioClip.stop();
}
}
https://riptutorial.com/ 50
String line = "";
while((line = bf.readLine()) != null) {
textArea.append(line + "\n");
}
} catch(Exception e) { /* omitted for brevity */ }
}
}
https://riptutorial.com/ 51
Chapter 8: Arrays
Introduction
Arrays allow for the storage and retrieval of an arbitrary quantity of values. They are analogous to
vectors in mathematics. Arrays of arrays are analogous to matrices, and act as multidimensional
arrays. Arrays can store any data of any type: primitives such as int or reference types such as
Object.
Syntax
• ArrayType[] myArray; // Declaring arrays
• ArrayType myArray[]; // Another valid syntax (less commonly used and discouraged)
• ArrayType[][][] myArray; // Declaring multi-dimensional jagged arrays (repeat []s)
• ArrayType myVar = myArray[index]; // Accessing (reading) element at index
• myArray[index] = value; // Assign value to position index of array
• ArrayType[] myArray = new ArrayType[arrayLength]; // Array initialization syntax
• int[] ints = {1, 2, 3}; // Array initialization syntax with values provided, length is inferred
from the number of provided values: {[value1[, value2]*]}
• new int[]{4, -5, 6} // Can be used as argument, without a local variable
• int[] ints = new int[3]; // same as {0, 0, 0}
• int[][] ints = {{1, 2}, {3}, null};// Multi-dimensional array initialization. int[] extends
Object (and so does anyType[]) so null is a valid value.
Parameters
Parameter Details
Type of the array. This can be primitive (int, long, byte) or Objects (String,
ArrayType
MyObject, etc).
Every array, when being created, needs a set length specified. This is either
length done when creating an empty array (new int[3]) or implied when specifying
values ({1, 2, 3}).
Examples
Creating and Initializing Arrays
Basic cases
https://riptutorial.com/ 52
int[] numbers1 = new int[3]; // Array for 3 int values, default value is 0
int[] numbers2 = { 1, 2, 3 }; // Array literal of 3 int values
int[] numbers3 = new int[] { 1, 2, 3 }; // Array of 3 int values initialized
int[][] numbers4 = { { 1, 2 }, { 3, 4, 5 } }; // Jagged array literal
int[][] numbers5 = new int[5][]; // Jagged array, one dimension 5 long
int[][] numbers6 = new int[5][4]; // Multidimensional array: 5x4
float[] boats = new float[5]; // Array of five 32-bit floating point numbers.
double[] header = new double[] { 4.56, 332.267, 7.0, 0.3367, 10.0 };
// Array of five 64-bit floating point numbers.
String[] theory = new String[] { "a", "b", "c" };
// Array of three strings (reference type).
Object[] dArt = new Object[] { new Object(), "We love Stack Overflow.", new Integer(3) };
// Array of three Objects (reference type).
For the last example, note that subtypes of the declared array type are allowed in the array.
Arrays for user defined types can also be built similar to primitive types
Java SE 8
// Streams - JDK 8+
Stream<Integer> toStream = Arrays.stream( initial );
Integer[] fromStream = toStream.toArray( Integer[]::new );
Intro
An array is a data structure that holds a fixed number of primitive values or references to object
instances.
https://riptutorial.com/ 53
Each item in an array is called an element, and each element is accessed by its numerical index.
The length of an array is established when the array is created:
The size of an array is fixed at runtime when initialized. It cannot be changed after
initialization. If the size must be mutable at runtime, a Collection class such as ArrayList should be
used instead. ArrayList stores elements in an array and supports resizing by allocating a new
array and copying elements from the old array.
the values are stored in the array itself. In the absence of an initializer (as in array2 above), the
default value assigned to each element is 0 (zero).
then the array contains references to objects of type SomeClassOrInterface. Those references can
refer to an instance of SomeClassOrInterface or any subclass (for classes) or implementing class
(for interfaces) of SomeClassOrInterface. If the array declaration has no initializer then the default
value of null is assigned to each element.
Because all arrays are int-indexed, the size of an array must be specified by an int. The size of
the array cannot be specified as a long:
Arrays use a zero-based index system, which means indexing starts at 0 and ends at length - 1.
For example, the following image represents an array with size 10. Here, the first element is at
index 0 and the last element is at index 9, instead of the first element being at index 1 and the last
element at index 10 (see figure below).
https://riptutorial.com/ 54
Accesses to elements of arrays are done in constant time. That means accessing to the first
element of the array has the same cost (in time) of accessing the second element, the third
element and so on.
Java offers several ways of defining and initializing arrays, including literal and constructor
notations. When declaring arrays using the new Type[length] constructor, each element will be
initialized with the following default values:
• 0 for primitive numerical types: byte, short, int, long, float, and double.
• '\u0000' (null character) for the char type.
• false for the boolean type.
• null for reference types.
When declaring an array, [] will appear as part of the type at the beginning of the declaration
(after the type name), or as part of the declarator for a particular variable (after variable name), or
both:
int array5[]; /*
equivalent to */ int[] array5;
int a, b[], c[][]; /*
equivalent to */ int a; int[] b; int[][] c;
int[] a, b[]; /*
equivalent to */ int[] a; int[][] b;
int a, []b, c[][]; /*
Compilation Error, because [] is not part of the type at beginning
of the declaration, rather it is before 'b'. */
// The same rules apply when declaring a method that returns an array:
int foo()[] { ... } /* equivalent to */ int[] foo() { ... }
In the following example, both declarations are correct and can compile and run without any
problems. However, both the Java Coding Convention and the Google Java Style Guide
discourage the form with brackets after the variable name—the brackets identify the array type
and should appear with the type designation. The same should be used for method return
signatures.
The discouraged type is meant to accommodate transitioning C users, who are familiar with the
syntax for C which has the brackets after the variable name.
https://riptutorial.com/ 55
int[] array2 = {}; // Equivalent syntax.
However, since it's an empty array, no elements can be read from it or assigned to it:
Such empty arrays are typically useful as return values, so that the calling code only has to worry
about dealing with an array, rather than a potential null value that may lead to a
NullPointerException.
The array size can be determined using a public final field called length:
Note: array.length returns the actual size of the array and not the number of array elements which
were assigned a value, unlike ArrayList.size() which returns the number of array elements which
were assigned a value.
It will create two three-length int arrays—a[0] and a[1]. This is very similar to the classical, C-style
initialization of rectangular multi-dimensional arrays.
Unlike C, where only rectangular multi-dimensional arrays are supported, inner arrays do not need
to be of the same length, or even defined:
Here, a[0] is a one-length int array, whereas a[1] is a two-length int array and a[2] is null. Arrays
like this are called jagged arrays or ragged arrays, that is, they are arrays of arrays. Multi-
dimensional arrays in Java are implemented as arrays of arrays, i.e. array[i][j][k] is equivalent to
https://riptutorial.com/ 56
((array[i])[j])[k]. Unlike C#, the syntax array[i,j] is not supported in Java.
Live on Ideone
In addition to the String literals and primitives shown above, the shortcut syntax for array
initialization also works with canonical Object types:
Because arrays are covariant, a reference type array can be initialized as an array of a subclass,
although an ArrayStoreException will be thrown if you try to set an element to something other than
a String:
The shortcut syntax cannot be used for this because the shortcut syntax would have an implicit
https://riptutorial.com/ 57
type of Object[].
An array can be initialized with zero elements by using String[] emptyArray = new String[0]. For
example, an array with zero length like this is used for Creating an Array from a Collection when
the method needs the runtime type of an object.
In both primitive and reference types, an empty array initialization (for example String[] array8 =
new String[3]) will initialize the array with the default value for each data type.
public MyGenericClass() {
a = new T[5]; // Compile time error: generic array creation
}
}
Instead, they can be created using one of the following methods: (note that these will generate
unchecked warnings)
This is the simplest method, but since the underlying array is still of type Object[], this
method does not provide type safety. Therefore, this method of creating an array is best
used only within the generic class - not exposed publicly.
Here the class of T has to be explicitly passed to the constructor. The return type of
Array.newInstance is always Object. However, this method is safer because the newly created
array is always of type T[], and therefore can be safely externalized.
Arrays.fill() can be used to fill an array with the same value after initialization:
https://riptutorial.com/ 58
Arrays.fill(array8, "abc"); // { "abc", "abc", "abc" }
Live on Ideone
fill() can also assign a value to each element of the specified range of the array:
Live on Ideone
Java SE 8
Since Java version 8, the method setAll, and its Concurrent equivalent parallelSetAll, can be used
to set every element of an array to generated values. These methods are passed a generator
function which accepts an index and returns the desired value for that position.
The following example creates an integer array and sets all of its elements to their respective
index value:
Live on Ideone
https://riptutorial.com/ 59
However, it is possible to create a new array and assign it to the variable being used to reference
the old array. While this results in the array referenced by that variable being re-initialized, the
variable contents are a completely new array. To do this, the new operator can be used with an
array initializer and assigned to the array variable:
Live on Ideone
• Object[] toArray()
Java SE 5
Java SE 5
// The array does not need to be created up front with the correct size.
// Only the array type matters. (If the size is wrong, a new array will
https://riptutorial.com/ 60
// be created with the same type.)
String[] stringArray = set.toArray(new String[0]);
The difference between them is more than just having untyped vs typed results. Their performance
can differ as well (for details please read this performance analysis section):
Java SE 8
Starting from Java SE 8+, where the concept of Stream has been introduced, it is possible to use
the Stream produced by the collection in order to create a new Array using the Stream.toArray
method.
Examples taken from two answers (1, 2) to Converting 'ArrayList to 'String[]' in Java on Stack
Overflow.
Arrays to a String
Java SE 5
Since Java 1.5 you can get a String representation of the contents of the specified array without
iterating over its every element. Just use Arrays.toString(Object[]) or
Arrays.deepToString(Object[]) for multidimentional arrays:
int[][] arr = {
{1, 2, 3},
{4, 5, 6},
{7, 8, 9}
};
System.out.println(Arrays.deepToString(arr)); // [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
Arrays.toString() method uses Object.toString() method to produce String values of every item in
the array, beside primitive type array, it can be used for all type of arrays. For instance:
https://riptutorial.com/ 61
@Override
public String toString() {
return "CAT!";
}
}
If no overridden toString() exists for the class, then the inherited toString() from Object will be
used. Usually the output is then not very useful, for example:
The Arrays.asList() method can be used to return a fixed-size List containing the elements of the
given array. The resulting List will be of the same parameter type as the base type of the array.
Note: This list is backed by (a view of) the original array, meaning that any changes to the list will
change the array and vice versa. However, changes to the list that would change its size (and
hence the array length) will throw an exception.
To create a copy of the list, use the constructor of java.util.ArrayList taking a Collection as an
argument:
Java SE 5
Java SE 7
In Java SE 7 and later, a pair of angle brackets <> (empty set of type arguments) can be used,
which is called the Diamond. The compiler can determine the type arguments from the context.
This means the type information can be left out when calling the constructor of ArrayList and it will
be inferred automatically during compilation. This is called Type Inference which is a part of Java
Generics.
// Using Arrays.asList()
https://riptutorial.com/ 62
// Using ArrayList.addAll()
// Using Collections.addAll()
A point worth noting about the Diamond is that it cannot be used with Anonymous Classes.
Java SE 8
// Using Streams
• A new List can be created by passing an array-backed List to the constructor of a new List.
This creates a new copy of the data, which has changeable size and that is not backed by
the original array:
The reason for this behavior is that primitive types cannot be used in place of generic type
parameters, so the entire primitive array replaces the generic type parameter in this case. In
order to convert a primitive array to a List, first of all, convert the primitive array to an array
of the corresponding wrapper type (i.e. call Arrays.asList on an Integer[] instead of an int[]
).
https://riptutorial.com/ 63
int[] arr = {1, 2, 3}; // primitive array of int
System.out.println(Arrays.asList(arr).contains(1));
View Demo
Integer[] arr = {1, 2, 3}; // object array of Integer (wrapper for int)
System.out.println(Arrays.asList(arr).contains(1));
View Demo
This will also print true, because the array will be interpreted as an Integer[]):
System.out.println(Arrays.asList(1,2,3).contains(1));
View Demo
It is possible to define an array with more than one dimension. Instead of being accessed by
providing a single index, a multidimensional array is accessed by specifying an index for each
dimension.
The declaration of multidimensional array can be done by adding [] for each dimension to a
regular array decleration. For instance, to make a 2-dimensional int array, add another set of
brackets to the declaration, such as int[][]. This continues for 3-dimensional arrays (int[][][])
and so forth.
int rows = 3;
int columns = 3;
int[][] table = new int[rows][columns];
The array can be indexed and assign values to it with this construct. Note that the unassigned
values are the default values for the type of an array, in this case 0 for int.
table[0][0] = 0;
table[0][1] = 1;
table[0][2] = 2;
It is also possible to instantiate a dimension at a time, and even make non-rectangular arrays.
These are more commonly referred to as jagged arrays.
It is important to note that although it is possible to define any dimension of jagged array, it's
https://riptutorial.com/ 64
preceding level must be defined.
// valid
String[][] employeeGraph = new String[30][];
// invalid
int[][] unshapenMatrix = new int[][10];
// also invalid
int[][][] misshapenGrid = new int[100][][10];
Multidimensional arrays and jagged arrays can also be initialized with a literal expression. The
following declares and populates a 2x3 int array:
int[][] table = {
{1, 2, 3},
{4, 5, 6}
};
Note: Jagged subarrays may also be null. For instance, the following code declares and
populates a two dimensional int array whose first subarray is null, second subarray is of zero
length, third subarray is of one length and the last subarray is a two length array:
int[][] table = {
null,
https://riptutorial.com/ 65
{},
{1},
{1,2}
};
For multidimensional array it is possible to extract arrays of lower-level dimension by their indices:
ArrayIndexOutOfBoundsException
Arrays are zero-based indexed, so the index of the first element is 0 and the index of the last
element is the array capacity minus 1 (i.e. array.length - 1).
Therefore, any request for an array element by the index i has to satisfy the condition 0 <= i <
array.length, otherwise the ArrayIndexOutOfBoundsException will be thrown.
Output:
Note that the illegal index that is being accessed is also included in the exception (2 in the
example); this information could be useful to find the cause of the exception.
To avoid this, simply check that the index is within the limits of the array:
int index = 2;
if (index >= 0 && index < people.length) {
System.out.println(people[index]);
}
https://riptutorial.com/ 66
Getting the Length of an Array
Arrays are objects which provide space to store up to its size of elements of specified type. An
array's size can not be modified after the array is created.
The length field in an array stores the size of an array. It is a final field and cannot be modified.
This code shows the difference between the length of an array and amount of objects an array
stores.
Result:
Array types inherit their equals() (and hashCode()) implementations from java.lang.Object, so
equals() will only return true when comparing against the exact same array object. To compare
arrays for equality based on their values, use java.util.Arrays.equals, which is overloaded for all
array types.
https://riptutorial.com/ 67
the same values
When the element type is a reference type, Arrays.equals() calls equals() on the array elements to
determine equality. In particular, if the element type is itself an array type, identity comparison will
be used. To compare multidimensional arrays for equality, use Arrays.deepEquals() instead as
below:
int a[] = { 1, 2, 3 };
int b[] = { 1, 2, 3 };
Because sets and maps use equals() and hashCode(), arrays are generally not useful as set
elements or map keys. Either wrap them in a helper class that implements equals() and hashCode()
in terms of the array elements, or convert them to List instances and store the lists.
Arrays to Stream
Java SE 8
Converting an array of primitives to Stream using Arrays.stream() will transform the array to a
primitive specialization of Stream:
You can also limit the Stream to a range of elements in the array. The start index is inclusive and
the end index is exclusive:
A method similar to Arrays.stream() appears in the Stream class: Stream.of(). The difference is that
Stream.of() uses a varargs parameter, so you can write something like:
https://riptutorial.com/ 68
You can iterate over arrays either by using enhanced for loop (aka foreach) or by using array
indices:
Java SE 5
It is worth noting here that there is no direct way to use an Iterator on an Array, but through the
Arrays library it can be easily converted to a list to obtain an Iterable object.
For primitive arrays (using java 8) use streams (specifically in this example - Arrays.stream ->
IntStream):
If you can't use streams (no java 8), you can choose to use google's guava library:
In two-dimensional arrays or more, both techniques can be used in a slightly more complex
fashion.
Example:
Java SE 5
https://riptutorial.com/ 69
for (int[] numbers : array) {
for (int value : numbers) {
System.out.println(value);
}
}
It is impossible to set an Array to any non-uniform value without using an index based loop.
Of course you can also use while or do-while loops when iterating using indices.
One note of caution: when using array indices, make sure the index is between 0 and
array.length - 1 (both inclusive). Don't make hard coded assumptions on the array length
otherwise you might break your code if the array length changes but your hard coded values don't.
Example:
// DON'T DO THIS :
for (int i = 0; i < 4; i++) {
numbers[i] += 1;
}
}
It's also best if you don't use fancy calculations to get the index but use the index to iterate and if
you need different values calculate those.
Example:
// DON'T DO THIS :
int doubleLength = array.length * 2;
for (int i = 0; i < doubleLength; i += 2) {
array[i / 2] = i;
}
}
https://riptutorial.com/ 70
}
Iterating over a temporary array instead of repeating code can make your code cleaner. It can be
used where the same operation is performed on multiple variables.
// copy-paste approach:
System.out.println(name);
System.out.println(eyeCount);
System.out.println(height);
System.out.println(legs);
System.out.println(arms);
Keep in mind that this code should not be used in performance-critical sections, as an array is
created every time the loop is entered, and that primitive variables will be copied into the array and
thus cannot be modified.
Copying arrays
for loop
int[] a = { 4, 1, 3, 2 };
int[] b = new int[a.length];
for (int i = 0; i < a.length; i++) {
b[i] = a[i];
}
Note that using this option with an Object array instead of primitive array will fill the copy with
reference to the original content instead of copy of it.
https://riptutorial.com/ 71
Object.clone()
Since arrays are Objects in Java, you can use Object.clone().
int[] a = { 4, 1, 3, 2 };
int[] b = a.clone(); // [4, 1, 3, 2]
Note that the Object.clone method for an array performs a shallow copy, i.e. it returns a reference
to a new array which references the same elements as the source array.
Arrays.copyOf()
java.util.Arrays provides an easy way to perform the copy of an array to another. Here is the
basic usage:
Note that Arrays.copyOf also provides an overload which allows you to change the type of the
array:
System.arraycopy()
public static void arraycopy(Object src, int srcPos, Object dest, int destPos, int
length) Copies an array from the specified source array, beginning at the specified
position, to the specified position of the destination array.
int[] a = { 4, 1, 3, 2 };
int[] b = new int[a.length];
System.arraycopy(a, 0, b, 0, a.length); // [4, 1, 3, 2]
Arrays.copyOfRange()
Mainly used to copy a part of an Array, you can also use it to copy whole array to another as
below:
https://riptutorial.com/ 72
int[] a = { 4, 1, 3, 2 };
int[] b = Arrays.copyOfRange(a, 0, a.length); // [4, 1, 3, 2]
Casting Arrays
Arrays are objects, but their type is defined by the type of the contained objects. Therefore, one
cannot just cast A[] to T[], but each A member of the specific A[] must be cast to a T object.
Generic example:
Java SE provides the method Arrays.copyOf(original, newLength, newType) for this purpose:
Java doesn't provide a direct method in java.util.Arrays to remove an element from an array. To
perform it, you can either copy the original array to a new one without the element to remove or
convert your array to another structure allowing the removal.
Using ArrayList
You can convert the array to a java.util.List, remove the element and convert the list back to an
array as follows:
// Creates a new array with the same size as the list and copies the list
// elements to it.
array = list.toArray(new String[list.size()]);
https://riptutorial.com/ 73
Using System.arraycopy
can be used to make a copy of the original array and remove the element you
System.arraycopy()
want. Below an example:
System.out.println(Arrays.toString(result)); //[1, 3, 4]
Array Covariance
Object arrays are covariant, which means that just as Integer is a subclass of Number, Integer[] is a
subclass of Number[]. This may seem intuitive, but can result in surprising behavior:
Although Integer[] is a subclass of Number[], it can only hold Integers, and trying to assign a Long
element throws a runtime exception.
Note that this behavior is unique to arrays, and can be avoided by using a generic List instead:
It's not necessary for all of the array elements to share the same type, as long as they are a
subclass of the array's type:
https://riptutorial.com/ 74
interface I {}
class A implements I {}
class B implements I {}
class C implements I {}
I[] array10 = new I[] { new A(), new B(), new C() }; // Create an array with new
// operator and array initializer.
I[] array11 = { new A(), new B(), new C() }; // Shortcut syntax with array
// initializer.
I[] array13 = new A[] { new A(), new A() }; // Works because A implements I.
Object[] array14 = new Object[] { "Hello, World!", 3.14159, 42 }; // Create an array with
// new operator and array initializer.
The simple answer is that you cannot do this. Once an array has been created, its size cannot be
changed. Instead, an array can only be "resized" by creating a new array with the appropriate size
and copying the elements from the existing array to the new one.
Suppose (for example) that a new element needs to be added to the listOfCities array defined as
above. To do this, you will need to:
There are various ways to do the above. Prior to Java 6, the most concise way was:
From Java 6 onwards, the Arrays.copyOf and Arrays.copyOfRange methods can do this more simply:
For other ways to copy an array, refer to the following example. Bear in mind that you need an
array copy with a different length to the original when resizing.
https://riptutorial.com/ 75
• Copying arrays
• It is inefficient. Making an array bigger (or smaller) involves copying many or all of the
existing array elements, and allocating a new array object. The larger the array, the more
expensive it gets.
• You need to be able to update any "live" variables that contain references to the old array.
One alternative is to create the array with a large enough size to start with. This is only viable if
you can determine that size accurately before allocating the array. If you cannot do that, then the
problem of resizing the array arises again.
The other alternative is to use a data structure class provided by the Java SE class library or a
third-party library. For example, the Java SE "collections" framework provides a number of
implementations of the List, Set and Map APIs with different runtime properties. The ArrayList class
is closest to performance characteristics of a plain array (e.g. O(N) lookup, O(1) get and set, O(N)
random insertion and deletion) while providing more efficient resizing without the reference update
problem.
(The resize efficiency for ArrayList comes from its strategy of doubling the size of the backing
array on each resize. For a typical use-case, this means that you only resize occasionally. When
you amortize over the lifetime of the list, the resize cost per insert is O(1). It may be possible to use
the same strategy when resizing a plain array.)
There are many ways find the location of a value in an array. The following example snippets all
assume that the array is one of the following:
In addition, each one sets index or index2 to either the index of required element, or -1 if the
element is not present.
https://riptutorial.com/ 76
int index2 = Arrays.asList(ints).indexOf(1); // compilation error
Using a Stream
Java SE 8
Note: Using a direct linear search is more efficient than wrapping in a list.
Java SE 8
https://riptutorial.com/ 77
isPresent = true;
break;
}
}
Sorting arrays
import java.util.Arrays;
String is not a numeric data, it defines it's own order which is called lexicographic order, also
known as alphabetic order. When you sort an array of String using sort() method, it sorts array
into natural order defined by Comparable interface, as shown below :
Increasing Order
Output:
Decreasing Order
Output:
String array after sorting in descending order : [Steve, Shane, John, Ben, Adam]
https://riptutorial.com/ 78
In order to sort an object array, all elements must implement either Comparable or Comparator
interface to define the order of the sorting.
We can use either sort(Object[]) method to sort an object array on its natural order, but you must
ensure that all elements in the array must implement Comparable.
Furthermore, they must be mutually comparable as well, for example e1.compareTo(e2) must not
throw a ClassCastException for any elements e1 and e2 in the array. Alternatively you can sort an
Object array on custom order using sort(T[], Comparator) method as shown in following example.
Arrays.sort(courses);
System.out.println("Object array after sorting in natural order : " +
Arrays.toString(courses));
Output:
Object array before sorting : [#101 Java@200 , #201 Ruby@300 , #301 Python@400 , #401
Scala@500 ]
Object array after sorting in natural order : [#101 Java@200 , #201 Ruby@300 , #301 Python@400
, #401 Scala@500 ]
Object array after sorting by price : [#101 Java@200 , #201 Ruby@300 , #301 Python@400 , #401
Scala@500 ]
Object array after sorting by name : [#101 Java@200 , #301 Python@400 , #201 Ruby@300 , #401
Scala@500 ]
To convert the array, it's possible to use streams (in Java 8 and above):
Java SE 8
With lower versions it can be by iterating the primitive array and explicitly copying it to the boxed
array:
https://riptutorial.com/ 79
Java SE 8
Java SE 8
Java SE 8
https://riptutorial.com/ 80
Chapter 9: Asserting
Syntax
• assert expression1;
• assert expression1 : expression2;
Parameters
Parameter Details
Optional. When used, AssertionErrors thrown by the assert statement have this
expression2
message.
Remarks
By default, assertions are disabled at runtime.
Assertions are statements that will throw an error if their expression evaluates to false. Assertions
should only be used to test code; they should never be used in production.
Examples
Checking arithmetic with assert
a = 1 - Math.abs(1 - a % 2);
return a;
https://riptutorial.com/ 81
Chapter 10: Atomic Types
Introduction
Java Atomic Types are simple mutable types that provide basic operations that are thread-safe
and atomic without resorting to locking. They are intended for use in cases where locking would be
a concurrency bottleneck, or where there is risk of deadlock or livelock.
Parameters
Parameter Description
compareAndSet If the value is the expeed value then sent it to the new value
Remarks
Many on essentially combinations of volatile reads or writes and CAS operations. Best way to
understand this is to look at the source code directly. E.g. AtomicInteger, Unsafe.getAndSet
Examples
Creating Atomic Types
In cases of more complex concurrency, using Atomic Variables is often a better alternative, as it
allows an individual variable to be accessed in a thread-safe manner without the overhead of
using synchronized methods or code blocks.
https://riptutorial.com/ 82
Similarly for other instance types.
There is a notable exception that there is no float and double types. These can be simulated
through the use of Float.floatToIntBits(float) and Float.intBitsToFloat(int) for float as well as
Double.doubleToLongBits(double) and Double.longBitsToDouble(long) for doubles.
If you are willing to use sun.misc.Unsafe you can use any primitive variable as atomic by using the
atomic operation in sun.misc.Unsafe. All primitive types should be converted or encoded in int or
longs to so use it in this way. For more on this see: sun.misc.Unsafe.
The simple way to implement multi-threaded applications is to use Java's built-in synchronization
and locking primitives; e.g. the synchronized keyword. The following example shows how we might
use synchronized to accumulate counts.
/**
* Increments the integer at the given index
*/
public synchronized void count(int number) {
if (number >= 0 && number < counters.length) {
counters[number]++;
}
}
/**
* Obtains the current count of the number at the given index,
* or if there is no number at that index, returns 0.
*/
public synchronized int getCount(int number) {
return (number >= 0 && number < counters.length) ? counters[number] : 0;
}
}
This implementation will work correctly. However, if you have a large number of threads making
lots of simultaneous calls on the same Counters object, the synchronization is liable to be a
bottleneck. Specifically:
1. Each synchronized method call will start with the current thread acquiring the lock for the
Counters instance.
https://riptutorial.com/ 83
2. The thread will hold the lock while it checks number value and updates the counter.
3. Finally, the it will release the lock, allowing other threads access.
If one thread attempts to acquire the lock while another one holds it, the attempting thread will be
blocked (stopped) at step 1 until the lock is released. If multiple threads are waiting, one of them
will get it, and the others will continue to be blocked.
• If there is a lot of contention for the lock (i.e. lots of thread try to acquire it), then some
threads can be blocked for a long time.
• When a thread is blocked waiting for the lock, the operating system will typically try switch
execution to a different thread. This context switching incurs a relatively large performance
impact on the processor.
• When there are multiple threads blocked on the same lock, there are no guarantees that any
one of them will be treated "fairly" (i.e. each thread is guaranteed to be scheduled to run).
This can lead to thread starvation.
/**
* Increments the integer at the given index
*/
public void count(int number) {
if (number >= 0 && number < counters.length) {
counters[number].incrementAndGet();
}
}
/**
* Obtains the current count of the object at the given index,
* or if there is no number at that index, returns 0.
*/
public int getCount(int number) {
return (number >= 0 && number < counters.length) ?
counters[number].get() : 0;
}
}
We have replaced the int[] with an AtomicInteger[], and initialized it with an instance in each
https://riptutorial.com/ 84
element. We have also added calls to incrementAndGet() and get() in place of operations on int
values.
But the most important thing is that we can remove the synchronized keyword because locking is
no longer required. This works because the incrementAndGet() and get() operations are atomic and
thread-safe. In this context, it means that:
• Each counter in the array will only be observable in the either the "before" state for an
operation (like an "increment") or in the "after" state.
• Assuming that the operation occurs at time T, no thread will be able to see the "before" state
after time T.
Furthermore, while two threads might actually attempt to update the same AtomicInteger instance
at the same time, the implementations of the operations ensure that only one increment happens
at a time on the given instance. This is done without locking, often resulting in better performance.
These low-level instructions are are used to implement higher-level operations in the APIs of the
respective AtomicXxx classes. For example, (again, in C-like pseudocode):
int increment() {
while (TRUE) {
int old = num;
int new = old + 1;
if (old == compare_and_swap(&num, old, new)) {
return new;
}
}
}
If there is no contention on the AtomicXxxx, the if test will succeed and the loop will end
immediately. If there is contention, then the if will fail for all but one of the threads, and they will
"spin" in the loop for a small number of cycles of the loop. In practice, the spinning is orders of
magnitude faster (except at unrealistically high levels of contention, where synchronized performs
better than atomic classes because when the CAS operation fails, then the retry will only add more
contention) than suspending the thread and switching to another one.
Incidentally, CAS instructions are typically used by the JVM to implement uncontended locking. If
the JVM can see that a lock is not currently locked, it will attempt to use a CAS to acquire the lock.
If the CAS succeeds, then there is no need to do the expensive thread scheduling, context
switching and so on. For more information on the techniques used, see Biased Locking in HotSpot
.
https://riptutorial.com/ 85
Read Atomic Types online: https://riptutorial.com/java/topic/5963/atomic-types
https://riptutorial.com/ 86
Chapter 11: Audio
Remarks
Instead of using the javax.sound.sampled Clip, you can also use the AudioClip which is from the
applet API. It is however recommended to use Clip since AudioClip is just older and presents
limited functionalities.
Examples
Play an Audio file Looped
Needed imports:
import javax.sound.sampled.AudioSystem;
import javax.sound.sampled.Clip;
This code will create a clip and play it continuously once started:
MIDI files can be played by using several classes from the javax.sound.midi package. A Sequencer
performs playback of the MIDI file, and many of its methods can be used to set playback controls
such as loop count, tempo, track muting, and others.
import java.io.File;
import java.io.IOException;
import javax.sound.midi.InvalidMidiDataException;
import javax.sound.midi.MidiSystem;
import javax.sound.midi.MidiUnavailableException;
import javax.sound.midi.Sequence;
import javax.sound.midi.Sequencer;
https://riptutorial.com/ 87
if (sequencer==null) {
System.err.println("Sequencer device not supported");
return;
}
sequencer.open(); // Open device
// Create sequence, the File must contain MIDI file data.
Sequence sequence = MidiSystem.getSequence(new File(args[0]));
sequencer.setSequence(sequence); // load it into sequencer
sequencer.start(); // start the playback
} catch (MidiUnavailableException | InvalidMidiDataException | IOException ex) {
ex.printStackTrace();
}
}
}
A sequencer can be set to mute one or more of the sequence's tracks during playback so none of
the instruments in those specified play. The following example sets the first track in the sequence
to be muted:
import javax.sound.midi.Track;
// ...
A sequencer can play a sequence repeatedly if the loop count is given. The following sets the
sequencer to play a sequence four times and indefinitely:
sequencer.setLoopCount(3);
sequencer.setLoopCount(Sequencer.LOOP_CONTINUOUSLY);
The sequencer does not always have to play the sequence from the beginning, nor does it have to
play the sequence until the end. It can start and end at any point by specifying the tick in the
sequence to start and end at. It is also possible to specify manually which tick in the sequence the
sequencer should play from:
sequencer.setLoopStartPoint(512);
sequencer.setLoopEndPoint(32768);
sequencer.setTickPosition(8192);
Sequencers can also play a MIDI file at a certain tempo, which can be controlled by specifying the
tempo in beats per minute (BPM) or microseconds per quarter note (MPQ). The factor at which the
sequence is played can be adjusted as well.
sequencer.setTempoInBPM(1250f);
sequencer.setTempoInMPQ(4750f);
sequencer.setTempoFactor(1.5f);
https://riptutorial.com/ 88
When you finished using the Sequencer, remeber to close it
sequencer.close();
You can also go almost bare-metal when producing sound with java. This code will write raw
binary data into the OS audio buffer to generate sound. It's extremely important to understand the
limitations and necessary calculations to generating sound like this. Since playback is basically
instantaneous, calculations need to be performed at almost real-time.
As such this method is unusable for more complicated sound-sampling. For such purposes using
specialized tools is the better approach.
The following method generates and directly outputs a rectangle-wave of a given frequency in a
given volume for a given duration.
For a more differentiated way to generate different soundwaves sinus calculations and possibly
larger sample sizes are necessary. This results in significantly more complex code and is
accordingly omitted here.
The Hello Audio! of Java that plays a sound file from local or internet storage looks as follows. It
https://riptutorial.com/ 89
works for uncompressed .wav files and should not be used for playing mp3 or compressed files.
import java.io.*;
import java.net.URL;
import javax.sound.sampled.*;
// Constructor
public SoundClipTest() {
try {
// Open an audio input stream.
File soundFile = new File("/usr/share/sounds/alsa/Front_Center.wav"); //you could
also get the sound file with an URL
AudioInputStream audioIn = AudioSystem.getAudioInputStream(soundFile);
AudioFormat format = audioIn.getFormat();
// Get a sound clip resource.
DataLine.Info info = new DataLine.Info(Clip.class, format);
Clip clip = (Clip)AudioSystem.getLine(info);
// Open audio clip and load samples from the audio input stream.
clip.open(audioIn);
clip.start();
} catch (UnsupportedAudioFileException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (LineUnavailableException e) {
e.printStackTrace();
}
}
https://riptutorial.com/ 90
Chapter 12: Autoboxing
Introduction
Autoboxing is the automatic conversion that Java compiler makes between primitive types and
their corresponding object wrapper classes. Example, converting int -> Integer, double -> Double...
If the conversion goes the other way, this is called unboxing. Typically, this is used in Collections
that cannot hold other than Objects, where boxing primitive types is needed before setting them in
the collection.
Remarks
Autoboxing can have performance issues when used frequently in your code.
• http://docs.oracle.com/javase/1.5.0/docs/guide/language/autoboxing.html
• Integer auto-unboxing and auto-boxing gives performance issues?
Examples
Using int and Integer interchangeably
As you use generic types with utility classes, you may often find that number types aren't very
helpful when specified as the object types, as they aren't equal to their primitive counterparts.
Java SE 7
Fortunately, expressions that evaluate to int can be used in place of an Integer when it is needed.
ints.add(Integer.valueOf(i));
And retains properties from Integer#valueOf such as having the same Integer objects cached by
the JVM when it is within the number caching range.
https://riptutorial.com/ 91
• short and Short
• float and Float
• double and Double
• long and Long
• char and Character
• boolean and Boolean
Care must be taken, however, in ambiguous situations. Consider the following code:
The java.util.List interface contains both a remove(int index) (List interface method) and a
remove(Object o) (method inherited from java.util.Collection). In this case no boxing takes place
and remove(int index) is called.
One more example of strange Java code behavior caused by autoboxing Integers with values in
range from -128 to 127:
Integer a = 127;
Integer b = 127;
Integer c = 128;
Integer d = 128;
System.out.println(a == b); // true
System.out.println(c <= d); // true
System.out.println(c >= d); // true
System.out.println(c == d); // false
This happens because >= operator implicitly calls intValue() which returns int while == compares
references, not the int values.
By default, Java caches values in range [-128, 127], so the operator == works because the
Integers in this range reference to the same objects if their values are same. Maximal value of the
cacheable range can be defined with -XX:AutoBoxCacheMax JVM option. So, if you run the program
with -XX:AutoBoxCacheMax=1000, the following code will print true:
Integer a = 1000;
Integer b = 1000;
System.out.println(a == b); // true
Boolean a = Boolean.TRUE;
if (a) { // a gets converted to boolean
System.out.println("It works!");
}
https://riptutorial.com/ 92
That works for while, do while and the condition in the for statements as well.
Note that, if the Boolean is null, a NullPointerException will be thrown in the conversion.
This is a minimalistic example, but in practice it often manifests in more sophisticated forms. The
NullPointerException is not very intuitive and is often little help in locating such bugs.
Rely on autoboxing and auto-unboxing with care, make sure that unboxed values will not have
null values at runtime.
will typically consume substantial amount of memory (about 60kb for 6k of actual data).
Furthermore, boxed integers usually require additional round-trips in the memory, and thus make
CPU caches less effective. In above example, the memory accessed is spread out to five different
locations that may be in entirely different regions of the memory: 1. the HashMap object, 2. the map's
Entry[] table object, 3. the Entry object, 4. the entrys key object (boxing the primitive key), 5. the
entrys value object (boxing the primitive value).
class Example {
int primitive; // Stored directly in the class `Example`
Integer boxed; // Reference to another memory location
}
Reading boxed requires two memory accesses, accessing primitive only one.
When getting data from this map, the seemingly innocent code
int sumOfSquares = 0;
for(int i = 256; i < 1024; i++) {
sumOfSquares += square.get(i);
https://riptutorial.com/ 93
}
is equivalent to:
int sumOfSquares = 0;
for(int i = 256; i < 1024; i++) {
sumOfSquares += square.get(Integer.valueOf(i)).intValue();
}
Typically, the above code causes the creation and garbage collection of an Integer object for
every Map#get(Integer) operation. (See Note below for more details.)
To reduce this overhead, several libraries offer optimized collections for primitive types that do not
require boxing. In addition to avoiding the boxing overhead, these collection will require about 4x
less memory per entry. While Java Hotspot may be able to optimize the autoboxing by working
with objects on the stack instead of the heap, it is not possible to optimize the memory overhead
and resulting memory indirection.
Java 8 streams also have optimized interfaces for primitive data types, such as IntStream that do
not require boxing.
Note: a typical Java runtime maintains a simple cache of Integer and other primitive wrapper
object that is used by the valueOf factory methods, and by autoboxing. For Integer, the default
range of this cache is -128 to +127. Some JVMs provide a JVM command-line option for changing
the cache size / range.
Example:
int i;
Integer j;
void ex_method(Integer i)//Is a valid statement
void ex_method1(int j)//Is a valid statement
When a method returns a primitive type variable then an object of corresponding wrapper class
can be passed as the return value interchangeably and vice versa.
Example:
int i;
Integer j;
int ex_method()
https://riptutorial.com/ 94
{...
return j;}//Is a valid statement
Integer ex_method1()
{...
return i;//Is a valid statement
}
Whenever performing operations on numbers the primitive type variable and object of respective
wrapper class can be used interchangeably.
int i=5;
Integer j=new Integer(7);
int k=i+j;//Is a valid statement
Integer m=i+j;//Is also a valid statement
While using wrapper class object and primitive variable interchangeably never forget or miss to
initialize or assign a value to the wrapper class object else it may lead to null pointer exception at
runtime.
Example:
In the above example, the value of the object is unassigned and uninitialized and thus at runtime
the program will run into null pointer exception.So as clear from the above example the value of
object should never be left uninitialized and unassigned.
https://riptutorial.com/ 95
Chapter 13: Basic Control Structures
Remarks
All control structures, unless otherwise noted, make use of block statements. These are denoted
by curly braces {}.
This differs from normal statements, which do not require curly braces, but also come with a stiff
caveat in that only the line immediately following the previous statement would be considered.
Thus, it is perfectly valid to write any of these control structures without curly braces, so long as
only one statement follows the beginning, but it is strongly discouraged, as it can lead to buggy
implementations, or broken code.
Example:
Examples
If / Else If / Else Control
if (i < 2) {
System.out.println("i is less than 2");
} else if (i > 2) {
System.out.println("i is more than 2");
} else {
System.out.println("i is not less than 2, and not more than 2");
}
The else if condition is checked only if all the conditions before it (in previous else if constructs,
and the parent if constructs) have been tested to false. In this example, the else if condition will
only be checked if i is greater than or equal to 2.
If its result is true, its block is run, and any else if and else constructs after it will be skipped.
https://riptutorial.com/ 96
If none of the if and else if conditions have been tested to true, the else block at the end will be
run.
For Loops
The three components of the for loop (separated by ;) are variable declaration/initialization (here
int i = 0), the condition (here i < 100), and the increment statement (here i++). The variable
declaration is done once as if placed just inside the { on the first run. Then the condition is
checked, if it is true the body of the loop will execute, if it is false the loop will stop. Assuming the
loop continues, the body will execute and finally when the } is reached the increment statement
will execute just before the condition is checked again.
The curly braces are optional (you can one line with a semicolon) if the loop contains just one
statement. But, it's always recommended to use braces to avoid misunderstandings and bugs.
The for loop components are optional. If your business logic contains one of these parts, you can
omit the corresponding component from your for loop.
Any looping statement having another loop statement inside called nested loop. The same way for
looping having more inner loop is called 'nested for loop'.
for(;;){
//Outer Loop Statements
for(;;){
//Inner Loop Statements
}
//Outer Loop Statements
}
https://riptutorial.com/ 97
}
}
While Loops
int i = 0;
while (i < 100) { // condition gets checked BEFORE the loop body executes
System.out.println(i);
i++;
}
A while loop runs as long as the condition inside the parentheses is true. This is also called the
"pre-test loop" structure because the conditional statement must be met before the main loop body
is performed every time.
The curly braces are optional if the loop contains just one statement, but some coding style
conventions prefers having the braces regardless.
do...while Loop
The do...while loop differs from other loops in that it is guaranteed to execute at least once. It is
also called the "post-test loop" structure because the conditional statement is performed after the
main loop body.
int i = 0;
do {
i++;
System.out.println(i);
} while (i < 100); // Condition gets checked AFTER the content of the loop executes.
In this example, the loop will run until the number 100 is printed (even though the condition is i <
100 and not i <= 100), because the loop condition is evaluated after the loop executes.
With the guarantee of at least one execution, it is possible to declare variables outside of the loop
and initialize them inside.
String theWord;
Scanner scan = new Scanner(System.in);
do {
theWord = scan.nextLine();
} while (!theWord.equals("Bird"));
System.out.println(theWord);
In this context, theWord is defined outside of the loop, but since it's guaranteed to have a value
based on its natural flow, theWord will be initialized.
For Each
Java SE 5
https://riptutorial.com/ 98
With Java 5 and up, one can use for-each loops, also known as enhanced for-loops:
strings.add("This");
strings.add("is");
strings.add("a for-each loop");
For each loops can be used to iterate over Arrays and implementations of the Iterable interface,
the later includes Collections classes, such as List or Set.
The loop variable can be of any type that is assignable from the source type.
The loop variable for a enhanced for loop for Iterable<T> or T[] can be of type S, if
• T extends S
• both T and S are primitive types and assignable without a cast
• S is a primitive type and T can be converted to a type assignable to S after unboxing
conversion.
• T is a primitive type and can be converted to S by autoboxing conversion.
Examples:
T elements = ...
for (S s : elements) {
}
T S Compiles
long[] int no
Iterable<CharSequence> String no
int[] Long no
If / Else
int i = 2;
https://riptutorial.com/ 99
if (i < 2) {
System.out.println("i is less than 2");
} else {
System.out.println("i is greater than 2");
}
The else block is optional and can be omitted. It runs if the if statement is false and does not run
if the if statement is true Because in that case if statement executes.
Switch statement
The switch statement is Java's multi-way branch statement. It is used to take the place of long if-
else if-else chains, and make them more readable. However, unlike if statements, one may not
use inequalities; each value must be concretely defined.
• case:
This is the value that is evaluated for equivalence with the argument to the switch
statement.
• default: This is an optional, catch-all expression, should none of the case statements
evaluate to true.
• Abrupt completion of the case statement; usually break: This is required to prevent the
undesired evaluation of further case statements.
With the exception of continue, it is possible to use any statement which would cause the abrupt
completion of a statement. This includes:
• break
• return
• throw
In the example below, a typical switch statement is written with four possible cases, including
default.
https://riptutorial.com/ 100
break;
default:
System.out.println("i is less than zero or greater than two");
}
By omitting break or any statement which would an abrupt completion, we can leverage what are
known as "fall-through" cases, which evaluate against several values. This can be used to create
ranges for a value to be successful against, but is still not as flexible as inequalities.
Java SE 5
enum Option {
BLUE_PILL,
RED_PILL
}
}
}
Java SE 7
https://riptutorial.com/ 101
public void rhymingGame(String phrase) {
switch (phrase) {
case "apples and pears":
System.out.println("Stairs");
break;
case "lorry":
System.out.println("truck");
break;
default:
System.out.println("Don't know any more");
}
}
Ternary Operator
Sometimes you have to check for a condition and set the value of a variable.
For ex.
String name;
if (A > B) {
name = "Billy";
} else {
name = "Jimmy";
}
The value of the variable is set to the value immediately after the condition, if the condition is true.
If the condition is false, the second value will be given to the variable.
Break
The break statement ends a loop (like for, while) or the evaluation of a switch statement.
Loop:
while(true) {
if(someCondition == 5) {
break;
}
}
The loop in the example would run forever. But when someCondition equals 5 at some point of
execution, then the loop ends.
If multiple loops are cascaded, only the most inner loop ends using break.
https://riptutorial.com/ 102
The try { ... } catch ( ... ) { ... } control structure is used for handling Exceptions.
A finally clause can be added after the catch. The finally clause would always be executed,
regardless of whether an exception was thrown.
outerloop:
for(...) {
innerloop:
for(...) {
if(condition1)
break outerloop;
if(condition2)
continue innerloop; // equivalent to: continue;
https://riptutorial.com/ 103
}
}
The continue statement is used to skip the remaining steps in the current iteration and start with
the next loop iteration. The control goes from the continue statement to the step value (increment
or decrement), if any.
The continue statement can also make the control of the program shift to the step value (if any) of
a named loop:
https://riptutorial.com/ 104
Chapter 14: Benchmarks
Introduction
Writing performance benchmarks in java is not as simple as getting System.currentTimeMillis() in
the beginning and in the end and calculating the difference. To write valid performance
benchmarks, one should use proper tools.
Examples
Simple JMH example
One of the tools for writing proper benchmark tests is JMH. Let's say we want to compare
performance of searching an element in HashSet vs TreeSet.
The easiest way to get JHM into your project - is to use maven and shade plugin. Also you can
see pom.xml from JHM examples.
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-shade-plugin</artifactId>
<version>3.0.0</version>
<executions>
<execution>
<phase>package</phase>
<goals>
<goal>shade</goal>
</goals>
<configuration>
<finalName>/benchmarks</finalName>
<transformers>
<transformer
implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
<mainClass>org.openjdk.jmh.Main</mainClass>
</transformer>
</transformers>
<filters>
<filter>
<artifact>*:*</artifact>
<excludes>
<exclude>META-INF/*.SF</exclude>
<exclude>META-INF/*.DSA</exclude>
<exclude>META-INF/*.RSA</exclude>
</excludes>
</filter>
</filters>
</configuration>
</execution>
</executions>
</plugin>
https://riptutorial.com/ 105
</plugins>
</build>
<dependencies>
<dependency>
<groupId>org.openjdk.jmh</groupId>
<artifactId>jmh-core</artifactId>
<version>1.18</version>
</dependency>
<dependency>
<groupId>org.openjdk.jmh</groupId>
<artifactId>jmh-generator-annprocess</artifactId>
<version>1.18</version>
</dependency>
</dependencies>
package benchmark;
import org.openjdk.jmh.annotations.*;
import org.openjdk.jmh.infra.Blackhole;
import java.util.HashSet;
import java.util.Random;
import java.util.Set;
import java.util.TreeSet;
import java.util.concurrent.TimeUnit;
@State(Scope.Thread)
public class CollectionFinderBenchmarkTest {
private static final int SET_SIZE = 10000;
@Setup
public void setupCollections() {
hashSet = new HashSet<>(SET_SIZE);
treeSet = new TreeSet<>();
@Benchmark
@BenchmarkMode(Mode.AverageTime)
@OutputTimeUnit(TimeUnit.NANOSECONDS)
public void testHashSet(Blackhole blackhole) {
blackhole.consume(hashSet.contains(stringToFind));
}
@Benchmark
https://riptutorial.com/ 106
@BenchmarkMode(Mode.AverageTime)
@OutputTimeUnit(TimeUnit.NANOSECONDS)
public void testTreeSet(Blackhole blackhole) {
blackhole.consume(treeSet.contains(stringToFind));
}
}
Please keep in mind this blackhole.consume(), we'll get back to it later. Also we need main class for
running benchmark:
package benchmark;
import org.openjdk.jmh.runner.Runner;
import org.openjdk.jmh.runner.RunnerException;
import org.openjdk.jmh.runner.options.Options;
import org.openjdk.jmh.runner.options.OptionsBuilder;
new Runner(options).run();
}
}
And we're all set. We just need to run mvn package (it will create benchmarks.jar in your /target
folder) and run our benchmark test:
And after some warmup and calculation iterations, we will have our results:
About that blackhole.consume(). If your calculations do not change the state of your application,
java will most likely just ignore it. So, in order to avoid it, you can either make your benchmark
methods return some value, or use Blackhole object to consume it.
You can find more information about writing proper benchmarks in Aleksey Shipilëv's blog, in
Jacob Jenkov's blog and in java-performance blog: 1, 2.
https://riptutorial.com/ 107
Chapter 15: BigDecimal
Introduction
The BigDecimal class provides operations for arithmetic (add, subtract, multiply, divide), scale
manipulation, rounding, comparison, hashing, and format conversion. The BigDecimal represents
immutable, arbitrary-precision signed decimal numbers. This class shall be used in a necessity of
high-precision calculation.
Examples
BigDecimal objects are immutable
If you want to calculate with BigDecimal you have to use the returned value because BigDecimal
objects are immutable:
Comparing BigDecimals
Commonly you should not use the equals method since it considers two BigDecimals equal only if
they are equal in value and also scale:
This example shows how to perform basic mathematical operations using BigDecimals.
1.Addition
https://riptutorial.com/ 108
BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");
//Equivalent to result = a + b
BigDecimal result = a.add(b);
System.out.println(result);
Result : 12
2.Subtraction
BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");
//Equivalent to result = a - b
BigDecimal result = a.subtract(b);
System.out.println(result);
Result : -2
3.Multiplication
When multiplying two BigDecimals the result is going to have scale equal to the sum of the scales
of operands.
//Equivalent to result = a * b
BigDecimal result = a.multiply(b);
System.out.println(result);
Result : 36.89931
To change the scale of the result use the overloaded multiply method which allows passing
MathContext - an object describing the rules for operators, in particular the precision and rounding
mode of the result. For more information about available rounding modes please refer to the
Oracle Documentation.
//Equivalent to result = a * b
BigDecimal result = a.multiply(b, returnRules);
System.out.println(result);
Result : 36.90
https://riptutorial.com/ 109
4.Division
Division is a bit more complicated than the other arithmetic operations, for instance consider the
below example:
We would expect this to give something similar to : 0.7142857142857143, but we would get:
This would work perfectly well when the result would be a terminating decimal say if I wanted to
divide 5 by 2, but for those numbers which upon dividing would give a non terminating result we
would get an ArithmeticException. In the real world scenario, one cannot predict the values that
would be encountered during the division, so we need to specify the Scale and the Rounding
Mode for BigDecimal division. For more information on the Scale and Rounding Mode, refer the
Oracle Documentation.
Result : 0.7142857143
5.Remainder or Modulus
BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");
//Equivalent to result = a % b
BigDecimal result = a.remainder(b);
System.out.println(result);
Result : 5
6.Power
https://riptutorial.com/ 110
BigDecimal a = new BigDecimal("5");
Result : 9765625
7.Max
BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");
Result : 7
8.Min
BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");
Result : 5
Result : 52.3449843776
https://riptutorial.com/ 111
System.out.println(result);
Result : 5234498.43776
There are many more options and combination of parameters for the above mentioned examples
(For instance, there are 6 variations of the divide method), this set is a non-exhaustive list and
covers a few basic examples.
Due to way that the float type is represented in computer memory, results of operations using this
type can be inaccurate - some values are stored as approximations. Good examples of this are
monetary calculations. If high precision is necessary, other types should be used. e.g. Java 7
provides BigDecimal.
import java.math.BigDecimal;
For a starting balance of 10000.00, after 1000 operations for 1.99, we expect the balance to be
8010.00. Using the float type gives us an answer around 8009.77, which is unacceptably
imprecise in the case of monetary calculations. Using BigDecimal gives us the proper result.
https://riptutorial.com/ 112
BigDecimal.valueOf()
The BigDecimal class contains an internal cache of frequently used numbers e.g. 0 to 10. The
BigDecimal.valueOf() methods are provided in preference to constructors with similar type
parameters i.e. in the below example a is preferred to b.
BigDecimal provides static properties for the numbers zero, one and ten. It's good practise to use
these instead of using the actual numbers:
• BigDecimal.ZERO
• BigDecimal.ONE
• BigDecimal.TEN
By using the static properties, you avoid an unnecessary instantiation, also you've got a literal in
your code instead of a 'magic number'.
//Bad example:
BigDecimal bad0 = new BigDecimal(0);
BigDecimal bad1 = new BigDecimal(1);
BigDecimal bad10 = new BigDecimal(10);
//Good Example:
BigDecimal good0 = BigDecimal.ZERO;
BigDecimal good1 = BigDecimal.ONE;
BigDecimal good10 = BigDecimal.TEN;
https://riptutorial.com/ 113
Chapter 16: BigInteger
Introduction
The BigInteger class is used for mathematical operations involving large integers with magnitudes
too large for primitive data types. For example 100-factorial is 158 digits - much larger than a long
can represent. BigInteger provides analogues to all of Java's primitive integer operators, and all
relevant methods from java.lang.Math as well as few other operations.
Syntax
• BigInteger variable_name = new BigInteger("12345678901234567890"); // a decimal integer
as a string
• BigInteger variable_name = new
BigInteger("1010101101010100101010011000110011101011000111110000101011010010",
2) // a binary integer as a string
• BigInteger variable_name = new BigInteger("ab54a98ceb1f0800", 16) // a hexadecimal
integer as a string
• BigInteger variable_name = new BigInteger(64, new Random()); // a pseudorandom number
generator supplying 64 bits to construct an integer
• BigInteger variable_name = new BigInteger(new byte[]{0, -85, 84, -87, -116, -21, 31, 10, -
46}); // signed two's complement representation of an integer (big endian)
• BigInteger variable_name = new BigInteger(1, new byte[]{-85, 84, -87, -116, -21, 31, 10, -
46}); // unsigned two's complement representation of a positive integer (big endian)
Remarks
BigIntegeris immutable. Therefore you can't change its state. For example, the following won't
work as sum won't be updated due to immutability.
sum = sum.add(BigInteger.valueOf(i));
Java SE 8
The official documentation of BigInteger states that BigInteger implementations should support all
integers between -22147483647 and 22147483647 (exclusive). This means BigIntegers can have
more than 2 billion bits!
https://riptutorial.com/ 114
Examples
Initialization
The java.math.BigInteger class provides operations analogues to all of Java's primitive integer
operators and for all relevant methods from java.lang.Math. As the java.math package is not
automatically made available you may have to import java.math.BigInteger before you can use the
simple class name.
which will widen the intValue integer to long, using sign bit extension for negative values, so that
negative values will stay negative.
Following constructor is used to translate the String representation of a BigInteger in the specified
radix into a BigInteger.
Java also supports direct conversion of bytes to an instance of BigInteger. Currently only signed
and unsigned big endian encoding may be used:
This will generate a BigInteger instance with value -128 as the first bit is interpreted as the sign bit.
This will generate a BigInteger instance with value 128 as the bytes are interpreted as unsigned
https://riptutorial.com/ 115
number, and the sign is explicitly set to 1, a positive number.
There's also BigInteger.TWO (value of "2"), but you can't use it in your code because it's private.
Comparing BigIntegers
You can compare BigIntegers same as you compare String or other objects in Java.
For example:
if(one.equals(two)){
System.out.println("Equal");
}
else{
System.out.println("Not Equal");
}
Output:
Not Equal
Note:
• == operator: compares references; i.e. whether two values refer to the same object
• equals() method: compares the content of two BigIntegers.
if (firstBigInteger == secondBigInteger) {
// Only checks for reference equality, not content equality!
}
Doing so may lead to unexpected behavior, as the == operator only checks for reference equality.
If both BigIntegers contain the same content, but do not refer to the same object, this will fail.
Instead, compare BigIntegers using the equals methods, as explained above.
You can also compare your BigInteger to constant values like 0,1,10.
for example:
https://riptutorial.com/ 116
BigInteger reallyBig = BigInteger.valueOf(1);
if(BigInteger.ONE.equals(reallyBig)){
//code when they are equal.
}
You can also compare two BigIntegers by using compareTo() method, as following: compareTo()
returns 3 values.
if(reallyBig.compareTo(reallyBig1) == 0){
//code when both are equal.
}
else if(reallyBig.compareTo(reallyBig1) == 1){
//code when reallyBig is greater than reallyBig1.
}
else if(reallyBig.compareTo(reallyBig1) == -1){
//code when reallyBig is less than reallyBig1.
}
BigInteger is in an immutable object, so you need to assign the results of any mathematical
operation, to a new BigInteger instance.
Addition: 10 + 10 = 20
output: 20
Substraction: 10 - 9 = 1
output: 1
Division: 10 / 5 = 2
https://riptutorial.com/ 117
BigInteger value1 = new BigInteger("10");
BigInteger value2 = new BigInteger("5");
output: 2
Division: 17/4 = 4
output: 4
Multiplication: 10 * 5 = 50
output: 50
Power: 10 ^ 3 = 1000
output: 1000
Remainder: 10 % 6 = 4
output: 4
System.out.println(value1.gcd(value2));
https://riptutorial.com/ 118
Output: 6
System.out.println(value1.max(value2));
Output: 11
System.out.println(value1.min(value2));
Output: 10
BigInteger supports the binary logic operations that are available to Number types as well. As with
all operations they are implemented by calling a method.
Binary Or:
val1.or(val2);
Binary And:
val1.and(val2);
Binary Xor:
val1.xor(val2);
https://riptutorial.com/ 119
RightShift:
LeftShift:
val1.not();
Output: 5
NAND (And-Not):*
val1.andNot(val2);
Output: 7
The BigInteger class has a constructor dedicated to generate random BigIntegers, given an
instance of java.util.Random and an int that specifies how many bits will the BigInteger have. Its
usage is quite simple - when you call the constructor BigInteger(int, Random) like this:
then you'll end up with a BigInteger whose value is between 0 (inclusive) and 2bitCount
(exclusive).
This also means that new BigInteger(2147483647, sourceOfRandomness) may return all positive
BigIntegers given enough time.
What will the sourceOfRandomness be is up to you. For example, a new Random() is good enough in
most cases:
https://riptutorial.com/ 120
new BigInteger(32, new Random());
If you're willing to give up speed for higher-quality random numbers, you can use a new
SecureRandom() instead:
import java.security.SecureRandom;
You can even implement an algorithm on-the-fly with an anonymous class! Note that rolling out
your own RNG algorithm will end you up with low quality randomness, so always be sure to
use an algorithm that is proven to be decent unless you want the resulting BigInteger(s) to be
predictable.
@Override
protected int next(int bits) {
seed = ((22695477 * seed) + 1) & 2147483647; // Values shamelessly stolen from
Wikipedia
return seed;
}
});
https://riptutorial.com/ 121
Chapter 17: Bit Manipulation
Remarks
• Unlike C/C++, Java is completely endian-neutral with respect to the underlying machine
hardware. You do not get big or little endian behavior by default; you have to explicitly
specify which behavior you want.
• The byte type is signed, with the range -128 to +127. To convert a byte value to its unsigned
equivalent, mask it with 0xFF like this: (b & 0xFF).
Examples
Packing / unpacking values as bit fragments
It is common for memory performance to compress multiple values into a single primitive value.
This may be useful to pass various information into a single variable.
For example, one can pack 3 bytes - such as color code in RGB - into an single int.
https://riptutorial.com/ 122
(byte)(x >> 16)
};
Checking, setting, clearing, and toggling individual bits. Using long as bit
mask
Assuming we want to modify bit n of an integer primitive, i (byte, short, char, int, or long):
Prints
FIRST_BIT: true
SECOND_BIT: false
THIRD_BIT: true
FOURTh_BIT: false
FIFTH_BIT: true
BIT_55: true
which matches that mask we passed as checkBitMask parameter: FIRST_BIT | THIRD_BIT | FIFTH_BIT
| BIT_55.
For expressing the power of 2 (2^n) of integers, one may use a bitshift operation that allows to
explicitly specify the n.
https://riptutorial.com/ 123
The syntax is basically:
Examples:
This is especially useful when defining constant values that should make it apparent, that a power
of 2 is used, instead of using hexadecimal or decimal values.
If an integer x is a power of 2, only one bit is set, whereas x-1 has all bits set after that. For
example: 4 is 100 and 3 is 011 as binary number, which satisfies the aforementioned condition. Zero
is not a power of 2 and has to be checked explicitly.
boolean isPowerOfTwo(int x)
{
return (x != 0) && ((x & (x - 1)) == 0);
}
Let’s suppose, we have three kind of permissions, READ, WRITE and EXECUTE. Each
permission can range from 0 to 7. (Let’s assume 4 bit number system)
How can we get the (12 bit number) permissions, set on above (12 bit number)?
https://riptutorial.com/ 124
0000 0000 0111 (&)
So, this is how we can get the EXECUTE permissions of the RESOURCE. Now, what if we want
to get READ permissions of the RESOURCE?
Right? You are probably assuming this? But, permissions are resulted in 1024. We want to get
only READ permissions for the resource. Don’t worry, that’s why we had the shift operators. If we
see, READ permissions are 8 bits behind the actual result, so if apply some shift operator, which
will bring READ permissions to the very right of the result? What if we do:
0100 0000 0000 >> 8 => 0000 0000 0100 (Because it’s a positive number so replaced
with 0’s, if you don’t care about sign, just use unsigned right shift operator)
Now, for example, we are given READ, WRITE, EXECUTE permissions for a RESOURCE, what
can we do to make permissions for this RESOURCE?
Let’s first take the example of binary permissions. (Still assuming 4 bit number system)
READ = 0001
WRITE = 0100
EXECUTE = 0110
But permissions are actually being represented (in our example) as 0001 0100 0110
So, in order to do this, we know that READ is placed 8 bits behind, WRITE is placed 4 bits behind
and PERMISSIONS is placed at the last. The number system being used for RESOURCE
permissions is actually 12 bit (in our example). It can(will) be different in different systems.
https://riptutorial.com/ 125
0001 0000 0000 (Left shift by 8 bits)
java.util.BitSet class
Since 1.7 there's a java.util.BitSet class that provides simple and user-friendly bit storage and
manipulation interface:
final BitSet bitSet = new BitSet(8); // by default all bits are unset
bitSet.set(3); // {0, 2, 3, 4, 6}
bitSet.flip(6); // {0, 2, 4}
BitSet implements Clonable and Serializable, and under the hood all bit values are stored in long[]
words field, that expands automatically.
bitSet.and(new BitSet(8));
bitSet.or(new BitSet(8));
bitSet.xor(new BitSet(8));
bitSet.andNot(new BitSet(8));
In Java, all number primitives are signed. For example, an int always represent values from [-2^31
- 1, 2^31], keeping the first bit to sign the value - 1 for negative value, 0 for positive.
https://riptutorial.com/ 126
Basic shift operators >> and << are signed operators. They will conserve the sign of the value.
But it is common for programmers to use numbers to store unsigned values. For an int, it means
shifting the range to [0, 2^32 - 1], to have twice as much value as with a signed int.
For those power users, the bit for sign as no meaning. That's why Java added >>>, a left-shift
operator, disregarding that sign bit.
This comes from the intended definition of right-shift. As it fills the emptied places on the left, there
are no decision to take regarding the bit of sign. As a consequence, there is no need for 2 different
operators.
https://riptutorial.com/ 127
Chapter 18: BufferedWriter
Syntax
• new BufferedWriter(Writer); //The default constructor
• BufferedWriter.write(int c); //Writes a single character
• BufferedWriter.write(String str); //Writes a string
• BufferedWriter.newLine(); //Writes a line separator
• BufferedWriter.close(); //Closes the BufferedWriter
Remarks
• If you try to write from a BufferedWriter (using BufferedWriter.write()) after closing the
BufferedWriter (using BufferedWriter.close()), it will throw an IOException.
• The BufferedWriter(Writer) constructor does NOT throw an IOException. However, the
FileWriter(File) constructor throws a FileNotFoundException, which extends IOException. So
catching IOException will also catch FileNotFoundException, there is never a need for a second
catch statement unless you plan on doing something different with the FileNotFoundException.
Examples
Write a line of text to File
This code writes the string to a file. It is important to close the writer, so this is done in a finally
block.
Also note that write(String s) does not place newline character after string has been written. To
put it use newLine() method.
Java SE 7
https://riptutorial.com/ 128
Path path = Paths.get("file.txt");
try (BufferedWriter bw = Files.newBufferedWriter(path)) {
bw.write(str);
}
}
https://riptutorial.com/ 129
Chapter 19: ByteBuffer
Introduction
The ByteBuffer class was introduced in java 1.4 to ease working on binary data. It's especially
suited to use with primitive type data. It allows the creation, but also subsequent manipulation of a
byte[]s on a higher abstraction level
Syntax
• byte[] arr = new byte[1000];
• ByteBuffer buffer = ByteBuffer.wrap(arr);
• ByteBuffer buffer = ByteBuffer.allocate(1024);
• ByteBuffer buffer = ByteBuffer.allocateDirect(1024);
• byte b = buffer.get();
• byte b = buffer.get(10);
• short s = buffer.getShort(10);
• buffer.put((byte) 120);
• buffer.putChar('a');
Examples
Basic Usage - Creating a ByteBuffer
There's two ways to create a ByteBuffer, where one can be subdivided again.
If you have an already existing byte[], you can "wrap" it into a ByteBuffer to simplify processing:
This would be a possibility for code that handles low-level networking interactions
If you do not have an already existing byte[], you can create a ByteBuffer over an array that's
specifically allocated for the buffer like this:
If the code-path is extremely performance critical and you need direct system memory access,
the ByteBuffer can even allocate direct buffers using #allocateDirect()
https://riptutorial.com/ 130
Basic Usage - Write Data to the Buffer
Given a ByteBuffer instance one can write primitive-type data to it using relative and absolute put.
The striking difference is that putting data using the relative method keeps track of the index the
data is inserted at for you, while the absolute method always requires giving an index to put the
data at.
Both methods allow "chaining" calls. Given a sufficiently sized buffer one can accordingly do the
following:
buffer.putInt(0xCAFEBABE).putChar('c').putFloat(0.25).putLong(0xDEADBEEFCAFEBABE);
buffer.putInt(0xCAFEBABE);
buffer.putChar('c');
buffer.putFloat(0.25);
buffer.putLong(0xDEADBEEFCAFEBABE);
Do note that the method operating on bytes is not named specially. Additionally note that it's also
valid to pass both a ByteBuffer and a byte[] to put. Other than that, all primitive types have
specialized put-methods.
An additional note: The index given when using absolute put* is always counted in bytes.
This operation will allocate 16 bytes of memory. The contents of direct buffers may reside outside
of the normal garbage-collected heap.
directBuffer.isDirect(); // true
The main characteristics of DirectByteBuffer is that JVM will try to natively work on allocated
memory without any additional buffering so operations performed on it may be faster then those
performed on ByteBuffers with arrays lying underneath.
It is recomended to use DirectByteBuffer with heavy IO operations that rely on speed of execution,
like real time communication.
We have to be aware that if we try using array() method we will get UnsupportedOperationException.
https://riptutorial.com/ 131
So it is a good practice to chech whether our ByteBuffer has it (byte array) before we try to access
it:
byte[] arrayOfBytes;
if(buffer.hasArray()) {
arrayOfBytes = buffer.array();
}
Another use of direct byte buffer is interop through JNI. Since a direct byte buffer does not use a
byte[], but an actual block of memory, it is possible to access that memory directly through a
pointer in native code. This can save a bit of trouble and overhead on marshalling between the
Java and native representation of data.
The JNI interface defines several functions to handle direct byte buffers: NIO Support.
https://riptutorial.com/ 132
Chapter 20: Bytecode Modification
Examples
What is Bytecode?
Bytecode is the set of instructions used by the JVM. To illustrate this let's take this Hello World
program.
ldc - Push a constant onto the stack. In this case, the String "Hello World"
invokevirtual - Invokes a method on a loaded reference on the stack and puts the result on the
stack. Parameters of the method are also taken from the stack.
For writing:
• Jasmin
https://riptutorial.com/ 133
• Krakatau
For editing:
• Libraries
○ASM
○Javassist
○BCEL - Doesn't support Java 8+
• Tools
○Bytecode-Viewer
○JBytedit
○reJ - Doesn't support Java 8+
○JBE - Doesn't support Java 8+
Firstly the classes from the jar need to be loaded. We'll use three methods for this process:
• loadClasses(File)
• readJar(JarFile, JarEntry, Map)
• getNode(byte[])
https://riptutorial.com/ 134
}
}
} catch (IOException e) {
e.printStackTrace();
}
return classes;
}
With these methods loading and changing a jar file becomes a simple matter of changing
ClassNodes in a map. In this example we will replace all Strings in the jar with capitalized ones
using the Tree API.
Now that all of the ClassNode's strings have been modified we need to save the changes. In order
to save the changes and have a working output a few things have to be done:
https://riptutorial.com/ 135
• saveAsJar(Map<String, byte[]> outBytes, String fileName)
Usage:
https://riptutorial.com/ 136
}
out.close();
} catch (IOException e) {
e.printStackTrace();
}
}
/**
* Load a class by from a ClassNode
*
* @param cn
* ClassNode to load
* @return
*/
public static Class<?> load(ClassNode cn) {
ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_FRAMES);
return new ClassDefiner(ClassLoader.getSystemClassLoader()).get(cn.name.replace("/", "."),
cw.toByteArray());
}
/**
* Classloader that loads a class from bytes.
*/
static class ClassDefiner extends ClassLoader {
public ClassDefiner(ClassLoader parent) {
super(parent);
}
https://riptutorial.com/ 137
ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_FRAMES);
ClassVisitor remapper = new ClassRemapper(cw, mapper);
cn.accept(remapper);
out.put(mappings.containsKey(cn.name) ? mappings.get(cn.name) : cn.name,
cw.toByteArray());
}
return out;
}
SimpleRemapper is an existing class in the ASM library. However it only allows for class names to
be changed. If you wish to rename fields and methods you should create your own implemenation
of the Remapper class.
Javassist Basic
Javassist is a bytecode instrumentation library that allows you to modify bytecode injecting Java
code that will be converted to bytecode by Javassist and added to the instrumented class/method
at runtime.
Lets write the first transformer that actually take an hypothetical class
"com.my.to.be.instrumented.MyClass" and add to the instructions of each method a log call.
import java.lang.instrument.ClassFileTransformer;
import java.lang.instrument.IllegalClassFormatException;
import java.security.ProtectionDomain;
import javassist.ClassPool;
import javassist.CtClass;
import javassist.CtMethod;
try {
// retrive default Javassist class pool
ClassPool cp = ClassPool.getDefault();
// get from the class pool our class with this qualified name
CtClass cc = cp.get("com.my.to.be.instrumented.MyClass");
// get all the methods of the retrieved class
CtMethod[] methods = cc.getDeclaredMethods()
for(CtMethod meth : methods) {
// The instrumentation code to be returned and injected
final StringBuffer buffer = new StringBuffer();
String name = meth.getName();
// just print into the buffer a log for example
buffer.append("System.out.println(\"Method " + name + " executed\" );");
meth.insertBefore(buffer.toString())
}
// create the byteclode of the class
https://riptutorial.com/ 138
byteCode = cc.toBytecode();
// remove the CtClass from the ClassPool
cc.detach();
} catch (Exception ex) {
ex.printStackTrace();
}
}
return byteCode;
}
}
Now in order to use this transformer (so that our JVM will call the method transform on each class
at load time) we need to add this instrumentor this with an agent:
import java.lang.instrument.Instrumentation;
Last step to start our first instrumentor experiment is to actually register this agent class to the
JVM machine execution. The easiest way to actually do it is to register it with an option into the
shell command:
As we can see the agent/transformer project is added as a jar to the execution of any application
named MyJavaApplication that is supposed to contain a class named
"com.my.to.be.instrumented.MyClass" to actually execute our injected code.
https://riptutorial.com/ 139
Chapter 21: C++ Comparison
Introduction
Java and C++ are similar languages. This topic serves as a quick reference guide for Java and
C++ Engineers.
Remarks
class Outer {
class Inner {
public:
Inner(Outer* o) :outer(o) {}
private:
Outer* outer;
};
};
Java
[non-static] Nested Class (aka Inner Class or Member Class)
class OuterClass {
...
class InnerClass {
...
}
}
https://riptutorial.com/ 140
Static Nested Class
class Outer {
class Inner {
...
};
};
Java
Static Nested Class (aka Static Member Class)[ref]
class OuterClass {
...
static class StaticNestedClass {
...
}
}
C++
Local Class[ref]
void fun() {
class Test {
/* members of Test class */
};
}
Java
Local Class[ref]
class Test {
void f() {
new Thread(new Runnable() {
public void run() {
doSomethingBackgroundish();
}
}).start();
}
}
https://riptutorial.com/ 141
Overriding vs Overloading
The following Overriding vs Overloading points apply to both C++ and Java:
• An overridden method has the same name and arguments as its base method.
• An overloaded method has the same name but different arguments and does not rely on
inheritance.
• Two methods with the same name and arguments but different return type are illegal. See
related Stackoverflow questions about "overloading with different return type in Java" -
Question 1; Question 2
Polymorphism
Polymorphism is the ability for objects of different classes related by inheritance to respond
differently to the same method call. Here's an example:
In C++, polymorphism is enabled by virtual methods. In Java, methods are virtual by default.
Order of Construction/Destruction
Object Cleanup
In C++, it's a good idea to declare a destructor as virtual to ensure that the subclass' destructor will
be called if the base-class pointer is deleted.
In Java, a finalize method is similar a destructor in C++; however, finalizers are unpredictable
(they rely on GC). Best practice - use a "close" method to explicitly cleanup.
https://riptutorial.com/ 142
finally {
super.finalize();
}
}
Abstract Method
declared without an pure virtual method abstract method
virtual void eat(void) = 0; abstract void draw();
implementation
Accessibility Modifiers
Modifier C++ Java
Public - accessible
no special notes no special notes
by all
Protected -
also accessible within
accessible by also accessible by friends
same package
subclasses
Private - accessible
also accessible by friends no special notes
by members
https://riptutorial.com/ 143
class Node {
private:
int key; Node *next;
// LinkedList::search() can access "key" & "next"
friend int LinkedList::search();
};
While C++ has always been susceptible to the diamond problem, Java was susceptible until Java
8. Originally, Java didn't support multiple inheritance, but with the advent of default interface
methods, Java classes can not inherit "implementation" from more than one class.
java.lang.Object Class
In Java all classes inherit, either implicitly or explicitly, from the Object class. Any Java reference
can be cast to the Object type.
Integer Types
C++ Type
Bits Min Max (on LLP64 or Java Type
LP64)
https://riptutorial.com/ 144
C++ Type
Bits Min Max (on LLP64 or Java Type
LP64)
-2(32-1) = -2.147
32 2(32-1)-1 = 2.147 billion int int
billion
unsigned long*
64 0 2(16)-1 --
unsigned long long
Examples
Static Class Members
C++ Example
// define in header
class Singleton {
public:
static Singleton *getInstance();
private:
Singleton() {}
static Singleton *instance;
};
// initialize in .cpp
Singleton* Singleton::instance = 0;
Java Example
https://riptutorial.com/ 145
private Singleton() {}
class Outer {
class Inner {
public:
Inner(Outer* o) :outer(o) {}
private:
Outer* outer;
};
};
Java
[non-static] Nested Class (aka Inner Class or Member Class)
class OuterClass {
...
class InnerClass {
...
}
}
class Outer {
class Inner {
...
https://riptutorial.com/ 146
};
};
Java
Static Nested Class (aka Static Member Class)[ref]
class OuterClass {
...
static class StaticNestedClass {
...
}
}
C++
Local Class[ref]
void fun() {
class Test {
/* members of Test class */
};
}
Java
Local Class[ref]
class Test {
void f() {
new Thread(new Runnable() {
public void run() {
doSomethingBackgroundish();
}
}).start();
}
}
Many argue that Java is ONLY pass-by-value, but it's more nuanced than that. Compare the
following C++ and Java examples to see the many flavors of pass-by-value (aka copy) and pass-
by-reference (aka alias).
https://riptutorial.com/ 147
C++ Example (complete code)
// passes a COPY of the object
static void passByCopy(PassIt obj) {
obj.i = 22; // only a "local" change
}
// passes a pointer
static void passByPointer(PassIt* ptr) {
ptr->i = 33;
ptr = 0; // better to use nullptr instead if '0'
}
https://riptutorial.com/ 148
Inheritance vs Composition
C++ & Java are both object-oriented languages, thus the following diagram applies to both.
Outcast Downcasting
Beware of using "downcasting" - Downcasting is casting down the inheritance hierarchy from a
base class to a subclass (i.e. opposite of polymorphism). In general, use polymorphism &
overriding instead of instanceof & downcasting.
C++ Example
// explicit type case required
Child *pChild = (Child *) &parent;
Java Example
if(mySubClass instanceof SubClass) {
SubClass mySubClass = (SubClass)someBaseClass;
mySubClass.nonInheritedMethod();
}
Abstract Method
declared without an implementation
C++
pure virtual method
Java
abstract method
https://riptutorial.com/ 149
Abstract Class
cannot be instantiated
C++
cannot be instantiated; has at least 1 pure virtual method
Java
cannot be instantiated; can have non-abstract methods
Interface
no instance fields
C++
nothing comparable to Java
Java
very similar to abstract class, but 1) supports multiple inheritance; 2) no instance fields
interface TestInterface {}
https://riptutorial.com/ 150
Chapter 22: Calendar and its Subclasses
Remarks
As of Java 8, Calendar and its subclasses have been superseded by the java.time package and its
subpackages. They should be preferred, unless a legacy API requires Calendar.
Examples
Creating Calendar objects
It's important to notice that months in Calendar are zero based, which means that JANUARY is
represented by an int value 0. In order to provide a better code, always use Calendar constants,
such as Calendar.JANUARY to avoid misunderstandings.
Note: Always use the month constants: The numeric representation is misleading, e.g.
Calendar.JANUARY has the value 0
The add() method affects all fields, and behaves effectively if one were to add or subtract actual
dates from the calendar
calendar.add(Calendar.MONTH, -6);
The above operation removes six months from the calendar, taking us back to 30 September
2015.
To change a particular field without affecting the other fields, use roll().
calendar.roll(Calendar.MONTH, -6);
The above operation removes six months from the current month, so the month is identified as
https://riptutorial.com/ 151
September. No other fields have been adjusted; the year has not changed with this operation.
Finding AM/PM
Subtracting calendars
Calendar c1 = Calendar.getInstance();
Calendar c2 = Calendar.getInstance();
c2.set(Calendar.DATE, c2.get(Calendar.DATE) + 1);
https://riptutorial.com/ 152
Chapter 23: Character encoding
Examples
Reading text from a file encoded in UTF-8
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
String line;
while ((line = reader.readLine()) != null) {
System.out.print(line);
}
}
import java.io.BufferedWriter;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
https://riptutorial.com/ 153
wr.write("Cyrillic symbol Ы");
}
}
}
import java.nio.charset.StandardCharsets;
import java.util.Arrays;
System.out.println(Arrays.toString(textInUtf8));
}
}
https://riptutorial.com/ 154
Chapter 24: Choosing Collections
Introduction
Java offers a wide variety of Collections. Choosing which Collection to use can be tricky. See the
Examples section for an easy-to-follow flowchart to choose the right Collection for the job.
Examples
Java Collections Flowchart
Use the following flowchart to choose the right Collection for the job.
https://riptutorial.com/ 155
Chapter 25: Class - Java Reflection
Introduction
The java.lang.Class class provides many methods that can be used to get metadata, examine and
change the run time behavior of a class.
The java.lang and java.lang.reflect packages provide classes for java reflection.
Where it is used
IDE (Integrated Development Environment) e.g. Eclipse, MyEclipse, NetBeans etc. Debugger Test
Tools etc.
Examples
getClass() method of Object class
class Simple { }
class Test {
void printName(Object obj){
Class c = obj.getClass();
System.out.println(c.getName());
}
public static void main(String args[]){
Simple s = new Simple();
https://riptutorial.com/ 156
Chapter 26: Classes and Objects
Introduction
Objects have states and behaviors. Example: A dog has states - color, name, breed as well as
behaviors – wagging the tail, barking, eating. An object is an instance of a class.
Class − A class can be defined as a template/blueprint that describes the behavior/state that the
object of its type support.
Syntax
• class Example {} //class keyword, name, body
Examples
Simplest Possible Class
class TrivialClass {}
A class consists at a minimum of the class keyword, a name, and a body, which might be empty.
class ObjectMemberVsStaticMember {
void increment() {
staticCounter ++;
memberCounter++;
}
}
o1.increment();
https://riptutorial.com/ 157
o2.increment();
o2.increment();
System.out.println("ObjectMemberVsStaticMember.staticCounter = " +
ObjectMemberVsStaticMember.staticCounter);
o1 static counter 3
o1 member counter 1
o2 static counter 3
o2 member counter 2
ObjectMemberVsStaticMember.staticCounter = 3
Note: You should not call static members on objects, but on classes. While it does not make a
difference for the JVM, human readers will appreciate it.
static members are part of the class and exists only once per class. Non-static members exist on
instances, there is an independent copy for each instance. This also means that you need access
to an object of that class to access its members.
Overloading Methods
Sometimes the same functionality has to be written for different kinds of inputs. At that time, one
can use the same method name with a different set of parameters. Each different set of
parameters is known as a method signature. As seen per the example, a single method can have
multiple signatures.
https://riptutorial.com/ 158
Displayer displayer = new Displayer();
displayer.displayName("Ram"); //prints "Name is: Ram"
displayer.displayName("Jon", "Skeet"); //prints "Name is: Jon Skeet"
}
}
The advantage is that the same functionality is called with two different numbers of inputs. While
invoking the method according to the input we are passing, (In this case either one string value or
two string values) the corresponding method is executed.
Note: Methods cannot be overloaded by changing just the return type (int method() is considered
the same as String method() and will throw a RuntimeException if attempted). If you change the
return type you must also change the parameters in order to overload.
Objects come in their own class, so a simple example would be a car (detailed explanations
below):
public Car(){
milesPerGallon = 0;
name = "";
color = "";
numGallonsInTank = 0;
}
https://riptutorial.com/ 159
public void drive(int distanceInMiles){
//get miles left in car
int miles = numGallonsInTank * milesPerGallon;
Objects are instances of their class. So, the way you would create an object would be by calling
the Car class in one of two ways in your main class (main method in Java or onCreate in
Android).
Option 1
Option 1 is where you essentially tell the program everything about the Car upon creation of the
object. Changing any property of the car would require calling one of the methods such as the
repaintCar method. Example:
https://riptutorial.com/ 160
newCar.repaintCar("Blue");
Note: Make sure you pass the correct data type to the method. In the example above, you may
also pass a variable to the repaintCar method as long as the data type is correct`.
That was an example of changing properties of an object, receiving properties of an object would
require using a method from the Car class that has a return value (meaning a method that is not
void). Example:
Option 1 is the best option when you have all the object's data at the time of creation.
Option 2
Option 2 gets the same effect but required more work to create an object correctly. I want to recall
this Constructor in the Car class:
Notice that you do not have to actually pass any parameters into the object to create it. This is
very useful for when you do not have all the aspects of the object but you need to use the parts
that you do have. This sets generic data into each of the instance variables of the object so that, if
you call for a piece of data that does not exist, no errors are thrown.
Note: Do not forget that you have to set the parts of the object later that you did not initialize it
with. For example,
This is a common mistake amongst objects that are not initialized with all their data. Errors were
avoided because there is a Constructor that allows an empty Car object to be created with stand-
in variables (public Car(){}), but no part of the myCar was actually customized. Correct example
of creating Car Object:
https://riptutorial.com/ 161
And, as a reminder, get an object's properties by calling a method in your main class. Example:
Constructors
Constructors are special methods named after the class and without a return type, and are used to
construct objects. Constructors, like methods, can take input parameters. Constructors are used to
initialize objects. Abstract classes can have constructors also.
It is important to understand that constructors are different from methods in several ways:
1. Constructors can only take the modifiers public, private, and protected, and cannot be
declared abstract, final, static, or synchronized.
3. Constructors MUST be named the same as the class name. In the Hello example, the Hello
object's constructor name is the same as the class name.
4. The this keyword has an additional usage inside constructors. this.method(...) calls a
method on the current instance, while this(...) refers to another constructor in the current
class with different signatures.
Constructors also can be called through inheritance using the keyword super.
public SuperManClass(){
// some implementation
}
// ... methods
}
https://riptutorial.com/ 162
}
To initialize a static final fields that require using more than a single expression, a static
initializer can be used to assign the value. The following example initializes a unmodifiable set of
Strings:
static {
Set<String> set = new HashSet<>();
set.add("Hello");
set.add("World");
set.add("foo");
set.add("bar");
set.add("42");
WORDS = Collections.unmodifiableSet(set);
}
}
Method Overriding and Overloading are two forms of polymorphism supported by Java.
Method Overloading
Method overloading (also known as static Polymorphism) is a way you can have two (or more)
methods (functions) with same name in a single class. Yes its as simple as that.
This way user can call the same method for area depending on the type of shape it has.
But the real question now is, how will java compiler will distinguish which method body is to be
executed?
https://riptutorial.com/ 163
Well Java have made it clear that even though the method names (area() in our case) can be
same but the arguments method is taking should be different.
Overloaded methods must have different arguments list (quantity and types).
That being said we cannot add another method to calculate area of a square like this : public
Double area(Long side) because in this case, it will conflict with area method of circle and will cause
ambiguity for java compiler.
Thank god, there are some relaxations while writing overloaded methods like
Well that's because which overloaded methods is to be invoked is decided at compile time, based
on the actual number of arguments and the compile-time types of the arguments.
Method Overriding
Well, method overriding (yes you guess it right, it is also known as dynamic polymorphism) is
somewhat more interesting and complex topic.
In method overriding we overwrite the method body provided by the parent class. Got it? No? Let's
go through an example.
So we have a class called Shape and it has method called area which will probably return the area
https://riptutorial.com/ 164
of the shape.
Let's say now we have two classes called Circle and Rectangle.
// See this annotation @Override, it is telling that this method is from parent
// class Shape and is overridden here
@Override
public Double area(){
return 3.14 * radius * radius;
}
}
// See this annotation @Override, it is telling that this method is from parent
// class Shape and is overridden here
@Override
public Double area(){
return length * breadth;
}
}
So, now both of your children classes have updated method body provided by the parent (Shape)
class. Now question is how to see the result? Well lets do it the old psvm way.
// Drumbeats ......
//This should print 78.5
System.out.println("Shape of circle : "+circle.area());
}
}
Wow! isn't it great? Two objects of same type calling same methods and returning different values.
My friend, that's the power of dynamic polymorphism.
https://riptutorial.com/ 165
Method Overloading Method Overriding
Method overloading is the example of compile time Method overriding is the example of
polymorphism. run time polymorphism.
https://riptutorial.com/ 166
Chapter 27: Classloaders
Remarks
A classloader is a class whose primary purpose is to mediate the location and loading of classes
used by an application. A class loader can also find and loaded resources.
The standard classloader classes can load classes and resources from directories in the file
system and from JAR and ZIP files. They can also download and cache JAR and ZIP files from a
remote server.
Classloaders are normally chained, so that the JVM will try to load classes from the standard class
libraries in preference to application-provided sources. Custom classloaders allow the programmer
to alter this. The also can do such things as decrypting bytecode files and bytecode modification.
Examples
Instantiating and using a classloader
This basic example shows how an application can instantiate a classloader and use it to
dynamically load a class.
The classloader created in this example will have the default classloader as its parent, and will first
try to find any class in the parent classloader before looking in "extra.jar". If the requested class
has already been loaded, the findClass call will return the reference to the previously loaded class.
The findClass call can fail in a variety of ways. The most common are:
• If the named class cannot be found, the call with throw ClassNotFoundException.
• If the named class depends on some other class that cannot be found, the call will throw
NoClassDefFoundError.
Every custom loader must directly or indirectly extend the java.lang.ClassLoader class. The main
extension points are the following methods:
https://riptutorial.com/ 167
The defineClass methods which are responsible for actually loading the class from a byte array are
final to prevent overloading. Any custom behavior needs to be performed prior to calling
defineClass.
@Override
protected Class findClass(String classname) throws ClassNotFoundException {
if (classname.equals(this.classname)) {
return defineClass(classname, classfile, 0, classfile.length);
} else {
throw new ClassNotFoundException(classname);
}
}
}
Since we have only overridden the findClass method, this custom class loader is going to behave
as follows when loadClass is called.
1. The classloader's loadClass method calls findLoadedClass to see if a class with this name has
already been loaded by this classloader. If that succeeds, the resulting Class object is
returned to the requestor.
2. The loadClass method then delegates to the parent classloader by calling its loadClass call. If
the parent can deal with the request, it will return a Class object which is then returned to the
requestor.
3. If the parent classloader cannot load the class, findClass then calls our override findClass
method, passing the name of the class to be loaded.
4. If the requested name matches this.classname, we call defineClass to load the actual class
from the this.classfile byte array. The resulting Class object is then returned.
5. If the name did not match, we throw ClassNotFoundException.
To load a class we first need to define it. The class is defined by the ClassLoader. There's just one
problem, Oracle didn't write the ClassLoader's code with this feature available. To define the class
we will need to access a method named defineClass() which is a private method of the ClassLoader
.
To access it, what we will do is create a new class, ByteClassLoader, and extend it to ClassLoader.
Now that we have extended our class to ClassLoader, we can access the ClassLoader's private
methods. To make defineClass() available, we will create a new method that will act like a mirror
for the private defineClass() method. To call the private method we will need the class name, name,
https://riptutorial.com/ 168
the class bytes, classBytes, the first byte's offset, which will be 0 because classBytes' data starts at
classBytes[0], and the last byte's offset, which will be classBytes.lenght because it represents the
size of the data, which will be the last offset.
Now, we have a public defineClass() method. It can be called by passing the name of the class
and the class bytes as arguments.
To call the method we need the class bytes so we create a Path object representing our class' path
by using the Paths.get() method and passing the path of the binary class as an argument. Now,
we can get the class bytes with Files.readAllBytes(path). So we create a ByteClassLoader instance
and use the method we created, defineClass(). We already have the class bytes but to call our
method we also need the class name which is given by the package name (dot) the class
canonical name, in this case stackoverflow.MyClass.
Note: The defineClass() method returns a Class<?> object. You can save it if you want.
To load the class, we just call loadClass() and pass the class name. This method can throw an
ClassNotFoundException so we need to use a try cath block
try{
loader.loadClass("stackoverflow.MyClass");
} catch(ClassNotFoundException e){
e.printStackTrace();
}
https://riptutorial.com/ 169
Chapter 28: Collection Factory Methods
Introduction
The arrival of Java 9 brings many new features to Java's Collections API, one of which being
collection factory methods. These methods allow for easy initialization of immutable collections,
whether they be empty or nonempty.
Note that these factory methods are only available for the following interfaces: List<E>, Set<E>, and
Map<K, V>
Syntax
• static <E> List<E> of()
• static <E> List<E> of(E e1)
• static <E> List<E> of(E e1, E e2)
• static <E> List<E> of(E e1, E e2, ..., E e9, E e10)
• static <E> List<E> of(E... elements)
• static <E> Set<E> of()
• static <E> Set<E> of(E e1)
• static <E> Set<E> of(E e1, E e2)
• static <E> Set<E> of(E e1, E e2, ..., E e9, E e10)
• static <E> Set<E> of(E... elements)
• static <K,V> Map<K,V> of()
• static <K,V> Map<K,V> of(K k1, V v1)
• static <K,V> Map<K,V> of(K k1, V v1, K k2, V v2)
• static <K,V> Map<K,V> of(K k1, V v1, K k2, V v2, ..., K k9, V v9, K k10, V v10)
• static <K,V> Map<K,V> ofEntries(Map.Entry<? extends K,? extends V>... entries)
Parameters
Map.of(Map.Entry<? extends K, ? A Map.Entry instance where its key can be K or one of its
extends V> entry) children, and its value can be V or any of its children.
Examples
List Factory Method Examples
https://riptutorial.com/ 170
• List<Integer> immutableEmptyList = List.of();
○ Initializes an empty, immutable List<Integer>.
• List<Integer> immutableList = List.of(1, 2, 3, 4, 5);
○ Initializes an immutable List<Integer> with five initial elements.
• List<Integer> mutableList = new ArrayList<>(immutableList);
○ Initializes a mutable List<Integer> from an immutable List<Integer>.
https://riptutorial.com/ 171
Chapter 29: Collections
Introduction
The collections framework in java.util provides a number of generic classes for sets of data with
functionality that can't be provided by regular arrays.
Collections framework contains interfaces for Collection<O>, with main sub-interfaces List<O> and
Set<O>, and mapping collection Map<K,V>. Collections are the root interface and are being
implemented by many other collection frameworks.
Remarks
Collections are objects that can store collections of other objects inside of them. You can specify
the type of data stored in a collection using Generics.
Java SE 1.4
Java 1.4.2 and below do not support generics. As such, you can not specify the type parameters
that a collection contains. In addition to not having type safety, you must also use casts to get the
correct type back from a collection.
In addition to Collection<E>, there are multiple major types of collections, some of which have
subtypes.
• List<E> is an ordered collection of objects. It is similar to an array, but does not define a size
limit. Implementations will usually grow in size internally to accomodate new elements.
• Set<E> is a collection of objects that does not allow duplicates.
○ SortedSet<E> is a Set<E> that also specifies element ordering.
• Map<K,V> is a collection of key/value pairs.
○ SortedMap<K,V> is a Map<K,V> that also specifies element ordering.
Java SE 5
Java SE 6
https://riptutorial.com/ 172
• Deque<E> is a Queue<E> that can be read from either end.
Note that the above items are all interfaces. In order to use them, you must find the appropriate
implementing classes, such as ArrayList, HashSet, HashMap, or PriorityQueue.
Each type of collection has multiple implementations that have different performance metrics and
use cases.
Note that the Liskov Substitution Principle applies to the collection subtypes. That is, a
SortedSet<E> can be passed to a function expecting a Set<E>. It is also useful to read about
Bounded Parameters in the Generics section for more information on how to use collections with
class inheritance.
If you want to create your own collections, it may be easier to inherit one of the abstract classes
(such as AbstractList) instead of implementing the interface.
Java SE 1.2
• instead of ArrayList
Vector
• Dictionary instead of Map. Note that Dictionary is also an abstract class rather than an
interface.
• Hashtable instead of HashMap
These classes are obsolete and should not be used in modern code.
Examples
Declaring an ArrayList and adding objects
Java SE 5
Java SE 7
aListOfFruits.add("Melon");
aListOfFruits.add("Strawberry");
In the above example, the ArrayList will contain the String "Melon" at index 0 and the String
https://riptutorial.com/ 173
"Strawberry" at index 1.
Also we can add multiple elements with addAll(Collection<? extends E> c) method
Standard Collections
Java Collections framework
A simple way to construct a List from individual data values is to use java.utils.Arrays method
Arrays.asList:
All standard collection implementations provide constructors that take another collection as an
argument adding all elements to the new collection at the time of construction:
import com.google.common.collect.Lists;
import com.google.common.collect.Sets;
...
List<String> list1 = Lists.newArrayList("ab", "bc", "cd");
List<String> list2 = Lists.newArrayList(data);
Set<String> set4 = Sets.newHashSet(data);
SortedSet<String> set5 = Sets.newTreeSet("bc", "cd", "ab", "bc", "cd");
Mapping Collections
https://riptutorial.com/ 174
Java Collections framework
Similarly for maps, given a Map<String, Object> map a new map can be constructed with all
elements as follows:
import org.apache.commons.lang3.ArrayUtils;
...
// Taken from org.apache.commons.lang.ArrayUtils#toMap JavaDoc
Each element of the array must be either a Map.Entry or an Array, containing at least two
elements, where the first element is used as key and the second as value.
import com.google.common.collect.Maps;
...
void howToCreateMapsMethod(Function<? super K,V> valueFunction,
Iterable<K> keys1,
Set<K> keys2,
SortedSet<K> keys3) {
ImmutableMap<K, V> map1 = toMap(keys1, valueFunction); // Immutable copy
Map<K, V> map2 = asMap(keys2, valueFunction); // Live Map view
SortedMap<K, V> map3 = toMap(keys3, valueFunction); // Live Map view
}
Java SE 8
Using Stream,
Stream.of("xyz", "abc").collect(Collectors.toList());
or
Arrays.stream("xyz", "abc").collect(Collectors.toList());
https://riptutorial.com/ 175
Join lists
Following ways can be used for joining lists without modifying source list(s).
ListUtils.union(listOne,listTwo);
Java SE 8
It is tricky to remove items from a list while within a loop, this is due to the fact that the index and
length of the list gets changed.
Given the following list, here are some examples that will give an unexpected result and some that
will give the correct result.
INCORRECT
Removing in iteration of for statement Skips "Banana":
The code sample will only print Apple and Strawberry. Banana is skipped because it moves to index 0
once Apple is deleted, but at the same time i gets incremented to 1.
https://riptutorial.com/ 176
for (int i = 0; i < fruits.size(); i++) {
System.out.println (fruits.get(i));
if ("Apple".equals(fruits.get(i))) {
fruits.remove(i);
}
}
Throws: java.util.ConcurrentModificationException
CORRECT
Removing in while loop using an Iterator
The Iterator interface has a remove() method built in just for this case. However, this method is
marked as "optional" in the documentation, and it might throw an UnsupportedOperationException.
Therefore, it is advisable to check the documentation to make sure this operation is supported (in
practice, unless the collection is an immutable one obtained through a 3rd party library or the use
of one of the Collections.unmodifiable...() method, the operation is almost always supported).
While using an Iterator a ConcurrentModificationException is thrown when the modCount of the List
is changed from when the Iterator was created. This could have happened in the same thread or
in a multi-threaded application sharing the same list.
A modCount is an int variable which counts the number of times this list has been structurally
https://riptutorial.com/ 177
modified. A structural change essentially means an add() or remove() operation being invoked on
Collection object (changes made by Iterator are not counted). When the Iterator is created, it
stores this modCount and on every iteration of the List checks if the current modCount is same as and
when the Iterator was created. If there is a change in the modCount value it throws a
ConcurrentModificationException.
Hence for the above-declared list, an operation like below will not throw any exception:
But adding a new element to the List after initializing an Iterator will throw a
ConcurrentModificationException:
Iterating backwards
This does not skip anything. The downside of this approach is that the output is reverse. However,
in most cases where you remove items that will not matter. You should never do this with
LinkedList.
This does not skip anything. When the ith element is removed from the List, the element originally
positioned at index i+1 becomes the new ith element. Therefore, the loop can decrement i in
order for the next iteration to process the next element, without skipping.
https://riptutorial.com/ 178
Using a "should-be-removed" list
This solution enables the developer to check if the correct elements are removed in a cleaner way.
Java SE 8
In Java 8 the following alternatives are possible. These are cleaner and more straight forward if
the removing does not have to happen in a loop.
Filtering a Stream
A List can be streamed and filtered. A proper filter can be used to remove all undesired elements.
List<String> filteredList =
fruits.stream().filter(p -> !"Apple".equals(p)).collect(Collectors.toList());
Note that unlike all the other examples here, this example produces a new List instance and
keeps the original List unchanged.
Using removeIf
Saves the overhead of constructing a stream if all that is needed is to remove a set of items.
Unmodifiable Collection
Sometimes it's not a good practice expose an internal collection since it can lead to a malicious
code vulnerability due to it's mutable characteristic. In order to provide "read-only" collections java
provides its unmodifiable versions.
An unmodifiable collection is often a copy of a modifiable collection which guarantees that the
collection itself cannot be altered. Attempts to modify it will result in an
UnsupportedOperationException exception.
It is important to notice that objects which are present inside the collection can still be altered.
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
https://riptutorial.com/ 179
public class MyPojoClass {
private List<Integer> intList = new ArrayList<>();
import java.util.List;
output:
Java SE 8
names.forEach(System.out::println);
names.parallelStream().forEach(System.out::println);
Java SE 5
https://riptutorial.com/ 180
System.out.println(name);
}
Java SE 5
Java SE 1.2
//Iterates list in backward direction once reaches the last element from above iterator in
forward direction
while(listIterator.hasPrevious()){
System.out.println(listIterator.previous());
}
Java SE 8
names.forEach(System.out::println);
Java SE 5
Java SE 5
Java SE 8
names.forEach((key, value) -> System.out.println("Key: " + key + " Value: " + value));
Java SE 5
Java SE 5
Sometimes it is appropriate to use an immutable empty collection. The Collections class provides
methods to get such collections in an efficient way:
These methods are generic and will automatically convert the returned collection to the type it is
assigned to. That is, an invocation of e.g. emptyList() can be assigned to any type of List and
likewise for emptySet() and emptyMap().
The collections returned by these methods are immutable in that they will throw
UnsupportedOperationException if you attempt to call methods which would change their contents (
add, put, etc.). These collections are primarily useful as substitutes for empty method results or
other default values, instead of using null or creating objects with new.
https://riptutorial.com/ 182
Collections in Java only work for objects. I.e. there is no Map<int, int> in Java. Instead, primitive
values need to be boxed into objects, as in Map<Integer, Integer>. Java auto-boxing will enable
transparent use of these collections:
Unfortunately, the overhead of this is substantial. A HashMap<Integer, Integer> will require about 72
bytes per entry (e.g. on 64-bit JVM with compressed pointers, and assuming integers larger than
256, and assuming 50% load of the map). Because the actual data is only 8 bytes, this yields a
massive overhead. Furthermore, it requires two level of indirection (Map -> Entry -> Value) it is
unnecessarily slow.
There exist several libraries with optimized collections for primitive data types (that require only
~16 bytes per entry at 50% load, i.e. 4x less memory, and one level of indirection less), that can
yield substantial performance benefits when using large collections of primitive values in Java.
Above I noticed an example to remove items from a List within a Loop and I thought of another
example that may come in handy this time using the Iterator interface.
This is a demonstration of a trick that might come in handy when dealing with duplicate items in
lists that you want to get rid of.
Note: This is only adding on to the Removing items from a List within a loop example:
The following method takes in two Collection objects and performs the magic of removing the
elements in our removeNameList that match with elements in nameList.
https://riptutorial.com/ 183
iterator.remove(); //remove the current Name or Item
}
}
Calling the method and passing in the nameList and the removeNameListas follows
removeNames(nameList,removeNameList);
Will produce the following output:
Array List before removing names: James Smith Sonny Huckle Berry Finn Allan
Array List after removing names: James Smith Finn Allan
A simple neat use for Collections that may come in handy to remove repeating elements within
lists.
Creating your own Iterable structure for use with Iterator or for-each loop.
To ensure that our collection can be iterated using iterator or for-each loop, we have to take care
of following steps:
1. The stuff we want to iterate upon has to be Iterable and expose iterator().
2. Design a java.util.Iterator by overriding hasNext(), next() and remove().
I have added a simple generic linked list implementation below that uses above entities to make
the linked list iterable.
package org.algorithms.linkedlist;
import java.util.Iterator;
import java.util.NoSuchElementException;
public class LinkedList<T> implements Iterable<T> {
Node<T> head, current;
private static class Node<T> {
T data;
Node<T> next;
Node(T data) {
this.data = data;
}
}
public LinkedList(T data) {
head = new Node<>(data);
}
public Iterator<T> iterator() {
return new LinkedListIterator();
}
private class LinkedListIterator implements Iterator<T> {
Node<T> node = head;
https://riptutorial.com/ 184
@Override
public boolean hasNext() {
return node != null;
}
@Override
public T next() {
if (!hasNext())
throw new NoSuchElementException();
Node<T> prevNode = node;
node = node.next;
return prevNode.data;
}
@Override
public void remove() {
throw new UnsupportedOperationException("Removal logic not implemented.");
}
}
public void add(T data) {
Node current = head;
while (current.next != null)
current = current.next;
current.next = new Node<>(data);
}
}
class App {
public static void main(String[] args) {
LinkedList<Integer> list = new LinkedList<>(1);
list.add(2);
list.add(4);
list.add(3);
//Test #1
System.out.println("using Iterator:");
Iterator<Integer> itr = list.iterator();
while (itr.hasNext()) {
Integer i = itr.next();
System.out.print(i + " ");
}
//Test #2
System.out.println("\n\nusing for-each:");
for (Integer data : list) {
System.out.print(data + " ");
}
}
}
Output
using Iterator:
1 2 4 3
using for-each:
1 2 4 3
https://riptutorial.com/ 185
This will run in Java 7+. You can make it run on Java 5 and Java 6 also by substituting:
with
This exception occurs when a collection is modified while iterating over it using methods other
than those provided by the iterator object. For example, we have a list of hats and we want to
remove all those that have ear flaps:
If we run this code, ConcurrentModificationException will be raised since the code modifies the
collection while iterating it. The same exception may occur if one of the multiple threads working
with the same list is trying to modify the collection while others iterate over it. Concurrent
modification of collections in multiple threads is a natural thing, but should be treated with usual
tools from the concurrent programming toolbox such as synchronization locks, special collections
adopted for concurrent modification, modifying the cloned collection from initial etc.
Sub Collections
https://riptutorial.com/ 186
Example:
Output:
Before Sublist [Hello1, Hello2]
After sublist changes [Hello1, Hello3, Hello2]
Set subSet(fromIndex,toIndex)
Here fromIndex is inclusive and toIndex is exclusive.
Map subMap(fromKey,toKey)
fromKey is inclusive and toKey is exclusive
If fromKey is greater than toKey or if this map itself has a restricted range, and fromKey or toKey
lies outside the bounds of the range then it throws IllegalArgumentException.
All the collections support backed collections means changes made on the sub collection will have
same change on the main collection.
https://riptutorial.com/ 187
Chapter 30: Command line Argument
Processing
Syntax
• public static void main(String[] args)
Parameters
Parameter Details
The command line arguments. Assuming that the main method is invoked by the
args
Java launcher, args will be non-null, and will have no null elements.
Remarks
When a regular Java application is launched using the java command (or equivalent), a main
method will be called, passing the arguments from the command line in the args array.
Unfortunately, the Java SE class libraries do not provide any direct support for command
argument processing. This leaves you two alternatives:
This Topic will attempt to cover some of the more popular 3rd-party libraries. For an extensive list
of the alternatives, see this answer to the StackOverflow Question "How to parse command line
arguments in Java?".
Examples
Argument processing using GWT ToolBase
If you want to parse more complex command-line arguments, e.g. with optional parameters, than
the best is to use google's GWT approach. All classes are public available at:
https://gwt.googlesource.com/gwt/+/2.8.0-
beta1/dev/core/src/com/google/gwt/util/tools/ToolBase.java
An example for handling the command-line myprogram -dir "~/Documents" -port 8888 is:
https://riptutorial.com/ 188
protected int port;
// getters for dir and port
...
public MyProgramHandler() {
this.registerHandler(new ArgHandlerDir() {
@Override
public void setDir(File dir) {
this.dir = dir;
}
});
this.registerHandler(new ArgHandlerInt() {
@Override
public String[] getTagArgs() {
return new String[]{"port"};
}
@Override
public void setInt(int value) {
this.port = value;
}
});
}
public static void main(String[] args) {
MyProgramHandler myShell = new MyProgramHandler();
if (myShell.processArgs(args)) {
// main program operation
System.out.println(String.format("port: %d; dir: %s",
myShell.getPort(), myShell.getDir()));
}
System.exit(1);
}
}
ArgHandleralso has a method isRequired() which can be overwritten to say that the command-line
argument is required (default return is false so that the argument is optional.
When the command-line syntax for an application is simple, it is reasonable to do the command
argument processing entirely in custom code.
In this example, we will present a series of simple case studies. In each case, the code will
produce error messages if the arguments are unacceptable, and then call System.exit(1) to tell the
shell that the command has failed. (We will assume in each case that the Java code is invoked
using a wrapper whose name is "myapp".)
https://riptutorial.com/ 189
System.exit(1);
}
// Run the application
System.out.println("It worked");
}
}
Note that if we neglected to check args.length, the command would crash if the user ran it with too
few command-line arguments.
package tommy;
public class Main {
public static void main(String[] args) {
boolean feelMe = false;
boolean seeMe = false;
int index;
loop: for (index = 0; index < args.length; index++) {
String opt = args[index];
switch (opt) {
case "-c":
seeMe = true;
break;
case "-f":
feelMe = true;
break;
default:
if (!opts.isEmpty() && opts.charAt(0) == '-') {
error("Unknown option: '" + opt + "');
}
break loop;
}
}
if (index >= args.length) {
error("Missing argument(s)");
}
https://riptutorial.com/ 190
// Run the application
// ...
}
As you can see, processing the arguments and options gets rather cumbersome if the command
syntax is complicated. It is advisable to use a "command line parsing" library; see the other
examples.
https://riptutorial.com/ 191
Chapter 31: Common Java Pitfalls
Introduction
This topic outlines some of the common mistakes made by beginners in Java.
This includes any common mistakes in use of the Java language or understanding of the run-time
environment.
Mistakes associated with specific APIs can be described in topics specific to those APIs. Strings
are a special case; they're covered in the Java Language Specification. Details other than
common mistakes can be described in this topic on Strings.
Examples
Pitfall: using == to compare primitive wrappers objects such as Integer
(This pitfall applies equally to all primitive wrapper types, but we will illustrate it for Integer and int
.)
When working with Integer objects, it is tempting to use == to compare values, because that is
what you would do with int values. And in some cases this will seem to work:
Here we created two Integer objects with the value 1 and compare them (In this case we created
one from a String and one from an int literal. There are other alternatives). Also, we observe that
the two comparison methods (== and equals) both yield true.
In this case, only the equals comparison yields the correct result.
The reason for this difference in behavior is, that the JVM maintains a cache of Integer objects for
the range -128 to 127. (The upper value can be overridden with the system property
"java.lang.Integer.IntegerCache.high" or the JVM argument "-XX:AutoBoxCacheMax=size"). For
values in this range, the Integer.valueOf() will return the cached value rather than creating a new
https://riptutorial.com/ 192
one.
Thus, in the first example the Integer.valueOf(1) and Integer.valueOf("1") calls returned the same
cached Integer instance. By contrast, in the second example the Integer.valueOf(1000) and
Integer.valueOf("1000") both created and returned new Integer objects.
The == operator for reference types tests for reference equality (i.e. the same object). Therefore, in
the first example int1_1 == int1_2 is true because the references are the same. In the second
example int2_1 == int2_2 is false because the references are different.
Every time a program opens a resource, such as a file or network connection, it is important to
free the resource once you are done using it. Similar caution should be taken if any exception
were to be thrown during operations on such resources. One could argue that the FileInputStream
has a finalizer that invokes the close() method on a garbage collection event; however, since we
can’t be sure when a garbage collection cycle will start, the input stream can consume computer
resources for an indefinite period of time. The resource must be closed in a finally section of a
try-catch block:
Java SE 7
Since Java 7 there is a really useful and neat statement introduced in Java 7 particularly for this
case, called try-with-resources:
Java SE 7
https://riptutorial.com/ 193
The try-with-resources statement can be used with any object that implements the Closeable or
AutoCloseable interface. It ensures that each resource is closed by the end of the statement. The
difference between the two interfaces is, that the close() method of Closeable throws an
IOException which has to be handled in some way.
In cases where the resource has already been opened but should be safely closed after use, one
can assign it to a local variable inside the try-with-resources
Java SE 7
The local resource variable created in the try-with-resources constructor is effectively final.
Java manages memory automatically. You are not required to free memory manually. An object's
memory on the heap may be freed by a garbage collector when the object is no longer reachable
by a live thread.
However, you can prevent memory from being freed, by allowing objects to be reachable that are
no longer needed. Whether you call this a memory leak or memory packratting, the result is the
same -- an unnecessary increase in allocated memory.
Memory leaks in Java can happen in various ways, but the most common reason is everlasting
object references, because the garbage collector can’t remove objects from the heap while there
are still references to them.
Static fields
One can create such a reference by defining class with a static field containing some collection of
objects, and forgetting to set that static field to null after the collection is no longer needed. static
fields are considered GC roots and are never collected. Another issue is leaks in non-heap
memory when JNI is used.
Classloader leak
By far, though, the most insidious type of memory leak is the classloader leak. A classloader holds
a reference to every class it has loaded, and every class holds a reference to its classloader.
Every object holds a reference to its class as well. Therefore, if even a single object of a class
loaded by a classloader is not garbage, not a single class that that classloader has loaded can be
collected. Since each class also refers to its static fields, they cannot be collected either.
Accumulation leak The accumulation leak example could look like the following:
https://riptutorial.com/ 194
final Deque<BigDecimal> numbers = new LinkedBlockingDeque<>();
final BigDecimal divisor = new BigDecimal(51);
scheduledExecutorService.scheduleAtFixedRate(() -> {
BigDecimal number = numbers.peekLast();
if (number != null && number.remainder(divisor).byteValue() == 0) {
System.out.println("Number: " + number);
System.out.println("Deque size: " + numbers.size());
}
}, 10, 10, TimeUnit.MILLISECONDS);
scheduledExecutorService.scheduleAtFixedRate(() -> {
numbers.add(new BigDecimal(System.currentTimeMillis()));
}, 10, 10, TimeUnit.MILLISECONDS);
try {
scheduledExecutorService.awaitTermination(1, TimeUnit.DAYS);
} catch (InterruptedException e) {
e.printStackTrace();
}
This example creates two scheduled tasks. The first task takes the last number from a deque
called numbers, and, if the number is divisible by 51, it prints the number and the deque's size. The
second task puts numbers into the deque. Both tasks are scheduled at a fixed rate, and they run
every 10 ms.
If the code is executed, you’ll see that the size of the deque is permanently increasing. This will
eventually cause the deque to be filled with objects that consume all available heap memory.
To prevent this while preserving the semantics of this program, we can use a different method for
taking numbers from the deque: pollLast. Contrary to the method peekLast, pollLast returns the
element and removes it from the deque while peekLast only returns the last element.
A common mistake for Java beginners is to use the == operator to test if two strings are equal. For
example:
The above program is supposed to test the first command line argument and print different
messages when it and isn't the word "hello". But the problem is that it won't work. That program
will output "Are you feeling grumpy today?" no matter what the first command line argument is.
https://riptutorial.com/ 195
In this particular case the String "hello" is put in the string pool while the String args[0] resides on
the heap. This means there are two objects representing the same literal, each with its reference.
Since == tests for references, not actual equality, the comparison will yield a false most of the
times. This doesn't mean that it will always do so.
When you use == to test strings, what you are actually testing is if two String objects are the same
Java object. Unfortunately, that is not what string equality means in Java. In fact, the correct way
to test strings is to use the equals(Object) method. For a pair of strings, we usually want to test if
they consist of the same characters in the same order.
But it actually gets worse. The problem is that == will give the expected answer in some
circumstances. For example
Interestingly, this will print "same", even though we are testing the strings the wrong way. Why is
that? Because the Java Language Specification (Section 3.10.5: String Literals) stipulates that any
two string >>literals<< consisting of the same characters will actually be represented by the same
Java object. Hence, the == test will give true for equal literals. (The string literals are "interned" and
added to a shared "string pool" when your code is loaded, but that is actually an implementation
detail.)
To add to the confusion, the Java Language Specification also stipulates that when you have a
compile-time constant expression that concatenates two string literals, that is equivalent to a
single literal. Thus:
https://riptutorial.com/ 196
if (s1 == s2) {
System.out.println("1. same");
} else {
System.out.println("1. different");
}
if (s1 + s3 == "hello mum") {
System.out.println("2. same");
} else {
System.out.println("2. different");
}
}
}
This will output "1. same" and "2. different". In the first case, the + expression is evaluated at
compile time and we compare one String object with itself. In the second case, it is evaluated at
run time and we compare two different String objects
In summary, using == to test strings in Java is almost always incorrect, but it is not guaranteed to
give the wrong answer.
Some people recommend that you should apply various tests to a file before attempting to open it
either to provide better diagnostics or avoid dealing with exceptions. For example, this method
attempts to check if path corresponds to a readable file:
File f = null;
try {
f = getValidatedFile("somefile");
} catch (IOException ex) {
System.err.println(ex.getMessage());
return;
}
try (InputStream is = new FileInputStream(file)) {
// Read data etc.
}
The first problem is in the signature for FileInputStream(File) because the compiler will still insist
we catch IOException here, or further up the stack.
The second problem is that checks performed by getValidatedFile do not guarantee that the
FileInputStream will succeed.
https://riptutorial.com/ 197
• Race conditions: another thread or a separate process could rename the file, delete the file,
or remove read access after the getValidatedFile returns. That would lead to a "plain"
IOException without the custom message.
• There are edge cases not covered by those tests. For example, on a system with SELinux in
"enforcing" mode, an attempt to read a file can fail despite canRead() returning true.
The third problem is that the tests are inefficient. For example, the exists, isFile and canRead calls
will each make a syscall to perform the required check. Another syscall is then made to open the
file, which repeats the same checks behind the scenes.
In short, methods like getValidatedFile are misguided. It is better to simply attempt to open the file
and handle the exception:
If you wanted to distinguish IO errors thrown while opening and reading, you could use a nested
try / catch. If you wanted to produce better diagnostics for open failures, you could perform the
exists, isFile and canRead checks in the handler.
If you mistakenly think of variables as objects, the actual behavior of the Java language will
surprise you.
• For Java variables which have a primitive type (such as int or float) the variable holds a
copy of the value. All copies of a primitive value are indistinguishable; i.e. there is only one
int value for the number one. Primitive values are not objects and they do not behave like
objects.
• For Java variables which have a reference type (either a class or an array type) the variable
holds a reference. All copies of a reference are indistinguishable. References may point to
objects, or they may be null which means that they point to no object. However, they are not
objects and they don't behave like objects.
Variables are not objects in either case, and they don't contain objects in either case. They may
https://riptutorial.com/ 198
contain references to objects, but that is saying something different.
Example class
The examples that follow use this class, which represents a point in 2D space.
An instance of this class is an object that has two fields x and y which have the type int.
We can have many instances of the MutableLocation class. Some will represent the same locations
in 2D space; i.e. the respective values of x and y will match. Others will represent different
locations.
In the above, we have declared three variables here, there and elsewhere that can hold references
to MutableLocation objects.
If you (incorrectly) think of these variables as being objects, then you are likely to misread the
statements as saying:
From that, you are likely to infer we have three independent objects in the three variables. In fact
there are only two objects created by the above. The variables here and there actually refer to the
same object.
https://riptutorial.com/ 199
System.out.println("BEFORE: here.x is " + here.x + ", there.x is " + there.x +
"elsewhere.x is " + elsewhere.x);
here.x = 42;
System.out.println("AFTER: here.x is " + here.x + ", there.x is " + there.x +
"elsewhere.x is " + elsewhere.x);
We assigned a new value to here.x and it changed the value that we see via there.x. They are
referring to the same object. But the value that we see via elsewhere.x has not changed, so
elsewhere must refer to a different object.
If a variable was an object, then the assignment here.x = 42 would not change there.x.
The equality operator does NOT test that two objects are
equal
Applying the equality (==) operator to reference values tests if the values refer to the same object.
It does not test whether two (different) objects are "equal" in the intuitive sense.
if (here == there) {
System.out.println("here is there");
}
if (here == elsewhere) {
System.out.println("here is elsewhere");
}
This will print "here is there", but it won't print "here is elsewhere". (The references in here and
elsewhere are for two distinct objects.)
By contrast, if we call the equals(Object) method that we implemented above, we are going to test
if two MutableLocation instances have an equal location.
if (here.equals(there)) {
System.out.println("here equals there");
}
if (here.equals(elsewhere)) {
System.out.println("here equals elsewhere");
}
This will print both messages. In particular, here.equals(elsewhere) returns true because the
semantic criteria we chose for equality of two MutableLocation objects has been satisfied.
https://riptutorial.com/ 200
Method calls do NOT pass objects at all
Java method calls use pass by value1 to pass arguments and return a result.
When you pass a reference value to a method, you're actually passing a reference to an object by
value, which means that it is creating a copy of the object reference.
As long as both object references are still pointing to the same object, you can modify that object
from either reference, and this is what causes confusion for some.
However, you are not passing an object by reference2. The distinction is that if the object
reference copy is modified to point to another object, the original object reference will still point to
the original object.
void g() {
MutableLocation foo = MutableLocation(1, 2);
f(foo);
System.out.println("foo.x is " + foo.x); // Prints "foo.x is 1".
}
void g() {
MutableLocation foo = new MutableLocation(0, 0);
f(foo);
System.out.println("foo.x is " + foo.x); // Prints "foo.x is 42"
}
1 - In languages like Python and Ruby, the term "pass by sharing" is preferred for "pass by value" of an object /
reference.
2 - The term "pass by reference" or "call by reference" has a very specific meaning in programming language
terminology. In effect, it means that you pass the address of a variable or an array element, so that when the called
method assigns a new value to the formal argument, it changes the value in the original variable. Java does not
support this. For a more fulsome description of different mechanisms for passing parameters, please refer to
https://en.wikipedia.org/wiki/Evaluation_strategy.
Occasionally we see StackOverflow Java questions (and C or C++ questions) that ask what
something like this:
i += a[i++] + b[i--];
https://riptutorial.com/ 201
evaluates to ... for some known initial states of i, a and b.
Generally speaking:
• for Java the answer is always specified1, but non-obvious, and often difficult to figure out
• for C and C++ the answer is often unspecified.
Such examples are often used in exams or job interviews as an attempt to see if the student or
interviewee understands how expression evaluation really works in the Java programming
language. This is arguably legitimate as a "test of knowledge", but that does not mean that you
should ever do this in a real program.
To illustrate, the following seemingly simple example has appeared a few times in StackOverflow
questions (like this one). In some cases, it appears as a genuine mistake in someone's code.
int a = 1;
a = a++;
System.out.println(a); // What does this print.
Most programmers (including Java experts) reading those statements quickly would say that it
outputs 2. In fact, it outputs 1. For a detailed explanation of why, please read this Answer.
However the real takeaway from this and similar examples is that any Java statement that both
assigns to and side-effects the same variable is going to be at best hard to understand, and at
worst downright misleading. You should avoid writing code like this.
1 - modulo potential issues with the Java Memory Model if the variables or objects are visible to other threads.
New Java programmers often forget, or fail to fully comprehend, that the Java String class is
immutable. This leads to problems like the one in the following example:
The above code is supposed to print command line arguments in upper case. Unfortunately, it
does not work, the case of the arguments is not changed. The problem is this statement:
s.toUpperCase();
You might think that calling toUpperCase() is going to change s to an uppercase string. It doesn't. It
https://riptutorial.com/ 202
can't! String objects are immutable. They cannot be changed.
In reality, the toUpperCase() method returns a String object which is an uppercase version of the
String that you call it on. This will probably be a new String object, but if s was already all
uppercase, the result could be the existing string.
So in order to use this method effectively, you need to use the object returned by the method call;
for example:
s = s.toUpperCase();
In fact, the "strings never change" rule applies to all String methods. If you remember that, then
you can avoid a whole category of beginner's mistakes.
https://riptutorial.com/ 203
Chapter 32: Comparable and Comparator
Syntax
• public class MyClass implements Comparable<MyClass>
• public class MyComparator implements Comparator<SomeOtherClass>
• public int compareTo(MyClass other)
• public int compare(SomeOtherClass o1, SomeOtherClass o2)
Remarks
When implementing a compareTo(..) method which depends upon a double, do not do the
following:
The truncation caused by the (int) cast will cause the method to sometimes incorrectly return 0
instead of a positive or negative number, and can thus lead to comparison and sorting bugs.
A non-generic version of Comparable<T>, simply Comparable, has existed since Java 1.2. Other than
for interfacing with legacy code, it's always better to implement the generic version Comparable<T>,
as it doesn't require casting upon comparison.
While it is possible to break from this paradigm, be cautious when doing so.
A Comparator<T> can still be used on instances of a class if that class implements Comparable<T>. In
this case, the Comparator's logic will be used; the natural ordering specified by the Comparable
implementation will be ignored.
Examples
https://riptutorial.com/ 204
Sorting a List using Comparable or a Comparator
Say we are working on a class representing a Person by their first and last names. We have
created a basic class to do this and implemented proper equals and hashCode methods.
@Override
public boolean equals(Object o) {
if (! (o instanceof Person)) return false;
Person p = (Person)o;
return firstName.equals(p.firstName) && lastName.equals(p.lastName);
}
@Override
public int hashCode() {
return Objects.hash(firstName, lastName);
}
}
Now we would like to sort a list of Person objects by their name, such as in the following scenario:
Unfortunately, as marked, the above currently won't compile. Collections.sort(..) only knows how
to sort a list if the elements in that list are comparable, or a custom method of comparison is given.
If you were asked to sort the following list : 1,3,5,4,2, you'd have no problem saying the answer is
1,2,3,4,5. This is because Integers (both in Java and mathematically) have a natural ordering, a
https://riptutorial.com/ 205
standard, default comparison base ordering. To give our Person class a natural ordering, we
implement Comparable<Person>, which requires implementing the method compareTo(Person p):
@Override
public boolean equals(Object o) {
if (! (o instanceof Person)) return false;
Person p = (Person)o;
return firstName.equals(p.firstName) && lastName.equals(p.lastName);
}
@Override
public int hashCode() {
return Objects.hash(firstName, lastName);
}
@Override
public int compareTo(Person other) {
// If this' lastName and other's lastName are not comparably equivalent,
// Compare this to other by comparing their last names.
// Otherwise, compare this to other by comparing their first names
int lastNameCompare = lastName.compareTo(other.lastName);
if (lastNameCompare != 0) {
return lastNameCompare;
} else {
return firstName.compareTo(other.firstName);
}
}
}
https://riptutorial.com/ 206
Collections.sort(people); //Now functions correctly
If, however, you either do not want or are unable to modify class Person, you can provide a custom
Comparator<T> that handles the comparison of any two Person objects. If you were asked to sort the
following list: circle, square, rectangle, triangle, hexagon you could not, but if you were asked to
sort that list based on the number of corners, you could. Just so, providing a comparator instructs
Java how to compare two normally not comparable objects.
//Assume the first version of Person (that does not implement Comparable) is used here
public static void main(String[] args) {
List<Person> people = Arrays.asList(new Person("John", "Doe"),
new Person("Bob", "Dole"),
new Person("Ronald", "McDonald"),
new Person("Alice", "McDonald"),
new Person("Jill", "Doe"));
Collections.sort(people); //Illegal, Person doesn't implement Comparable.
Collections.sort(people, new PersonComparator()); //Legal
//Assume the first version of Person (that does not implement Comparable) is used here
public static void main(String[] args) {
List<Person> people = Arrays.asList(new Person("John", "Doe"),
new Person("Bob", "Dole"),
new Person("Ronald", "McDonald"),
new Person("Alice", "McDonald"),
new Person("Jill", "Doe"));
Collections.sort(people); //Illegal, Person doesn't implement Comparable.
//Anonymous Class
https://riptutorial.com/ 207
Collections.sort(people, new Comparator<Person>() { //Legal
public int compare(Person p1, Person p2) {
//Method code...
}
});
}
Java SE 8
//Lambda
Collections.sort(people, (p1, p2) -> { //Legal
//Method code....
});
Collections.sort(people, Comparator.comparing(Person::getLastName)
.thenComparing(Person::getFirstName));
https://riptutorial.com/ 208
}
These two methods do essentially the same thing, with one minor difference: compareTo compares
this to other, whereas compare compares t1 to t2, not caring at all about this.
Aside from that difference, the two methods have similar requirements. Specifically (for
compareTo), Compares this object with the specified object for order. Returns a negative integer,
zero, or a positive integer as this object is less than, equal to, or greater than the specified object.
Thus, for the comparison of a and b:
• If a < b, a.compareTo(b) and compare(a,b) should return a negative integer, and b.compareTo(a)
and compare(b,a) should return a positive integer
• If a > b, a.compareTo(b) and compare(a,b) should return a positive integer, and b.compareTo(a)
and compare(b,a) should return a negative integer
• If a equals b for comparison, all comparisons should return 0.
• One that takes a List<T> as a parameter where T must implement Comparable and override
the compareTo() method that determines sort order.
• One that takes a List and a Comparator as the arguments, where the Comparator
determines the sort order.
@Override
public int compareTo(Person o) {
return this.getAge() - o.getAge();
}
@Override
public String toString() {
return this.getAge()+"-"+this.getName();
}
https://riptutorial.com/ 209
Here is how you would use the above class to sort a List in the natural ordering of its elements,
defined by the compareTo() method override:
//-- usage
List<Person> pList = new ArrayList<Person>();
Person p = new Person();
p.setName("A");
p.setAge(10);
pList.add(p);
p = new Person();
p.setName("Z");
p.setAge(20);
pList.add(p);
p = new Person();
p.setName("D");
p.setAge(30);
pList.add(p);
System.out.println(pList);
Here is how you would use an anonymous inline Comparator to sort a List that does not
implement Comparable, or in this case, to sort a List in an order other than the natural ordering:
//-- explicit sorting, define sort on another property here goes with name
Collections.sort(pList, new Comparator<Person>() {
@Override
public int compare(Person o1, Person o2) {
return o1.getName().compareTo(o2.getName());
}
});
System.out.println(pList);
As of Java 8, there are default methods on the Map.Entry interface to allow sorting of map
iterations.
Java SE 8
https://riptutorial.com/ 210
Of course, these can also be used outside of the stream api :
Java SE 8
Comparator.comparing(Person::getName)
This creates a comparator for the class Person that uses this person name as the comparison
source. Also it is possible to use method version to compare long, int and double. For example:
Comparator.comparingInt(Person::getAge)
Reversed order
To create a comparator that imposes the reverse ordering use reversed() method:
Comparator.comparing(Person::getName).reversed()
Chain of comparators
Comparator.comparing(Person::getLastName).thenComparing(Person::getFirstName)
This will create a comparator that firs compares with last name then compares with first name.
You can chain as many comparators as you want.
https://riptutorial.com/ 211
Chapter 33: CompletableFuture
Introduction
CompletableFuture is a class added to Java SE 8 which implements the Future interface from
Java SE 5. In addition to supporting the Future interface it adds many methods that allow
asynchronous callback when the future is completed.
Examples
Convert blocking method to asynchonous
The following method will take a second or two depending on your connection to retrieve a web
page and count the text length. Whatever thread calls it will block for that period of time. Also it
rethrows an exception which is useful later on.
This converts it to a method that will return immediately by moving the blocking method call to
another thread. By default the supplyAsync method will run the supplier on the common pool. For
a blocking method this is probably not a good choice since one might exhaust the threads in that
pool which is why I added the optional service parameter.
To use the function in an asynchronous fashion one should use on of the methods that accepts a
lamda to be called with the result of the of the supplier when it completes such as thenAccept.
Also it is important to use exceptionally or handle method to log any exceptions that might have
happened.
https://riptutorial.com/ 212
asyncGetWebPageLength("https://stackoverflow.com/")
.thenAccept(l -> {
System.out.println("Stack Overflow returned " + l);
})
.exceptionally((Throwable throwable) -> {
Logger.getLogger("myclass").log(Level.SEVERE, "", throwable);
return null;
});
In the example below, the calculateShippingPrice method calculates shipping cost, which takes
some processing time. In a real world example, this would e.g. be contacting another server which
returns the price based on the weight of the product and the shipping method.
By modeling this in an async way via CompletableFuture, we can continue different work in the
method (i.e. calculating packaging costs).
// Let's just say each 200 grams is a new dollar on your shipping costs
int shippingCosts = weightInGrams / 200;
try {
Thread.sleep(2000L); // Now let's simulate some waiting time...
} catch(InterruptedException e) { /* We can safely ignore that */ }
https://riptutorial.com/ 213
Chapter 34: Concurrent Collections
Introduction
A concurrent collection is a [collection][1] which permits access by more than one thread at the
same time. Different threads can typically iterate through the contents of the collection and add or
remove elements. The collection is responsible for ensuring that the collection doesn't become
corrupt. [1]:
http://stackoverflow.com/documentation/java/90/collections#t=201612221936497298484
Examples
Thread-safe Collections
When you make a thread-safe collection, you should never access it through the original
collection, only through the thread-safe wrapper.
Java SE 5
Starting in Java 5, java.util.collections has several new thread-safe collections that don't need
the various Collections.synchronized methods.
Concurrent Collections
Concurrent collections are a generalization of thread-safe collections, that allow for a broader
usage in a concurrent environment.
While thread-safe collections have safe element addition or removal from multiple threads, they do
not necessarily have safe iteration in the same context (one may not be able to safely iterate
through the collection in one thread, while another one modifies it by adding/removing elements).
As iteration is often the base implementation of several bulk methods in collections, like addAll,
https://riptutorial.com/ 214
removeAll,or also collection copying (through a constructor, or other means), sorting, ... the use
case for concurrent collections is actually pretty large.
The "snapshot" style iterator method uses a reference to the state of the array at the
point that the iterator was created. This array never changes during the lifetime of the
iterator, so interference is impossible and the iterator is guaranteed not to throw
ConcurrentModificationException.
https://riptutorial.com/ 215
Another concurrent collection regarding iteration is ConcurrentLinkedQueue, which states :
Iterators are weakly consistent, returning elements reflecting the state of the queue at
some point at or since the creation of the iterator. They do not throw
java.util.ConcurrentModificationException, and may proceed concurrently with other
operations. Elements contained in the queue since the creation of the iterator will be
returned exactly once.
One should check the javadocs to see if a collection is concurrent, or not. The attributes of the
iterator returned by the iterator() method ("fail fast", "weakly consistent", ...) is the most important
attribute to look for.
Could (and statistically will on most modern, multi CPU/core architectures) lead to exceptions.
Synchronized collections from the Collections utility methods are thread safe for addition/removal
of elements, but not iteration (unless the underlying collection being passed to it already is).
else
{
//'value' reference is mapped to key = 1.
}
}
}
https://riptutorial.com/ 216
Read Concurrent Collections online: https://riptutorial.com/java/topic/8363/concurrent-collections
https://riptutorial.com/ 217
Chapter 35: Concurrent Programming
(Threads)
Introduction
Concurrent computing is a form of computing in which several computations are executed
concurrently instead of sequentially. Java language is designed to support concurrent
programming through the usage of threads. Objects and resources can be accessed by multiple
threads; each thread can potentially access any object in the program and the programmer must
ensure read and write access to objects is properly synchronized between threads.
Remarks
Related topic(s) on StackOverflow:
• Atomic Types
• Executor, ExecutorService and Thread pools
• Extending Thread versus implementing Runnable
Examples
Basic Multithreading
If you have many tasks to execute, and all these tasks are not dependent of the result of the
precedent ones, you can use Multithreading for your computer to do all this tasks at the same
time using more processors if your computer can. This can make your program execution faster if
you have some big independent tasks.
CountAndPrint(String name) {
this.name = name;
}
https://riptutorial.com/ 218
// of CountAndPrint in another thread
new Thread(new CountAndPrint("Instance " + i)).start();
}
The code of the run method of the various CountAndPrint instances will execute in non predictable
order. A snippet of a sample execution might look like this:
Instance 4: 1
Instance 2: 1
Instance 4: 2
Instance 1: 1
Instance 1: 2
Main: 1
Instance 4: 3
Main: 2
Instance 3: 1
Instance 4: 4
...
Producer-Consumer
A simple example of producer-consumer problem solution. Notice that JDK classes (AtomicBoolean
and BlockingQueue) are used for synchronization, which reduces the chance of creating an invalid
solution. Consult Javadoc for various types of BlockingQueue; choosing different implementation
may drastically change the behavior of this example (like DelayQueue or Priority Queue).
https://riptutorial.com/ 219
}
}
producer.start();
consumer.start();
Thread.sleep(1000);
producer.interrupt();
Thread.sleep(10);
consumer.interrupt();
}
}
Using ThreadLocal
A useful tool in Java Concurrency is ThreadLocal – this allows you to have a variable that will be
unique to a given thread. Thus, if the same code runs in different threads, these executions will not
share the value, but instead each thread has its own variable that is local to the thread.
https://riptutorial.com/ 220
For example, this is frequently used to establish the context (such as authorization information) of
handling a request in a servlet. You might do something like this:
Now, instead of passing MyUserContext into every single method, you can instead use
MyServlet.getContext() where you need it. Now of course, this does introduce a variable that needs
to be documented, but it’s thread-safe, which eliminates a lot of the downsides to using such a
highly scoped variable.
The key advantage here is that every thread has its own thread local variable in that contexts
container. As long as you use it from a defined entry point (like demanding that each servlet
maintains its context, or perhaps by adding a servlet filter) you can rely on this context being there
when you need it.
CountDownLatch
CountDownLatch
A synchronization aid that allows one or more threads to wait until a set of operations
being performed in other threads completes.
Key Methods:
Causes the current thread to wait until the latch has counted down to zero, unless the
thread is interrupted.
https://riptutorial.com/ 221
public void countDown()
Decrements the count of the latch, releasing all waiting threads if the count reaches
zero.
Example:
import java.util.concurrent.*;
}
CountDownLatch latch = new CountDownLatch(numberOfThreads);
for (int n = 0; n < numberOfThreads; n++) {
Thread t = new Thread(new DoSomethingInAThread(latch));
t.start();
}
latch.await();
System.out.println("In Main thread after completion of " + numberOfThreads + "
threads");
} catch(Exception err) {
err.printStackTrace();
}
}
}
output:
java CountDownLatchDemo 5
Do some thing
Do some thing
Do some thing
Do some thing
https://riptutorial.com/ 222
Do some thing
In Main thread after completion of 5 threads
Explanation:
Synchronization
In Java, there is a built-in language-level locking mechanism: the synchronized block, which can
use any Java object as an intrinsic lock (i.e. every Java object may have a monitor associated with
it).
Intrinsic locks provide atomicity to groups of statements. To understand what that means for us,
let's have a look at an example where synchronized is useful:
In this case, if it weren't for the synchronized block, there would have been multiple concurrency
issues involved. The first one would be with the post increment operator (it isn't atomic in itself),
and the second would be that we would be observing the value of t after an arbitrary amount of
other threads has had the chance to modify it. However, since we acquired an intrinsic lock, there
will be no race conditions here and the output will contain numbers from 1 to 100 in their normal
order.
Intrinsic locks in Java are mutexes (i.e. mutual execution locks). Mutual execution means that if
one thread has acquired the lock, the second will be forced to wait for the first one to release it
before it can acquire the lock for itself. Note: An operation that may put the thread into the wait
(sleep) state is called a blocking operation. Thus, acquiring a lock is a blocking operation.
Intrinsic locks in Java are reentrant. This means that if a thread attempts to acquire a lock it
already owns, it will not block and it will successfully acquire it. For instance, the following code will
https://riptutorial.com/ 223
not block when called:
The following blocks of code are practically equivalent (even though the bytecode seems to be
different):
2. synchronized method:
class MyClass {
...
public static void bar() {
synchronized(MyClass.class) {
doSomeOtherStuff();
}
}
}
class MyClass {
...
public static synchronized void bar() {
doSomeOtherStuff();
}
}
Atomic operations
https://riptutorial.com/ 224
An atomic operation is an operation that is executed "all at once", without any chance of other
threads observing or modifying state during the atomic operation's execution.