Friday, April 13, 2007

SNIPPET, java.lang.Math

SNIPPET, java.lang.Math

Sometimes it is necessary to take time off from the usual and play with the application programming interface. We’ll be using some of the functionalities here when we start real time coding.

package transkawa;

class MathAPI {
static double container = 2.0098765d;
public static void main(String[] args){
System.out.println("Base log to e is: "+Math.E);
System.out.println("PI is "+Math.PI+" in double
primitive.");

//the absolute value of PI is
System.out.println("PI in absolute values
is:"+Math.abs(Math.PI));
System.out.println("log e in abs value is:
"+Math.abs(Math.E));
System.out.println("Absolute value of our container
"+Math.abs(container));

//the smallest double value that is greater than or equal
//to the double value of container and equal to an integer
System.out.println("The ceiling value of container is:
"+Math.ceil(container));
System.out.println("While the floor is:
"+Math.floor(container));

//raising the floor by 2
System.out.println("Let's raise the floor of container to
2: "+Math.pow(Math.floor(container), 2));

//the cosine assuming container is an angle
System.out.println("The cosine of container is:
"+Math.cos(container));

//we can test for mathematical greater than
System.out.println("The greater of PI and log e is:
"+Math.max(Math.PI, Math.E));

//a random number generator also exists for Math class
//you get random numbers all the time:)
System.out.println("What u see is what u get:
"+Math.random());

//let's do a narrowing primitive conversion on container
System.out.println("double to long gives:
"+Math.round(container));

//a little square root pleae
System.out.println("square root of 2.0098756 is:
"+Math.sqrt(container));

System.out.println(Math.ulp(container));
}

}

SNIPPET, java.lang.StringBuilder

SNIPPET, java.lang.StringBuilder

This class defines a mutable sequence of characters. It was created as a drop-in replacement for StringBuffer class in places where the StringBuffer would be used for single threaded actions.

The principal operations in a StringBuilder are the append and insert methods which are overloaded and accept data of any type. A given datum is effectively converted to a string and the characters of that string inserted or appended to the StringBuilder where the append method add these characters at the end of the builder and the insert method at a specified point.

Here is a simple class, BuilderExample, that is based on the principles of the StringBuilder class.

package transkawa;

class BuilderExample {
static StringBuilder stringchain = new StringBuilder("A");
static final String initialchain = stringchain.toString();
String spaces = " ";
static String current="Current string chain: ";

//to append strings in this class, first attach a space
//then attach the string. Append always at the last position
void appendString(String str){
stringchain.append(spaces);
stringchain.append(str);
}

//this method appends a char without spaces
void appendChar(char ch){
stringchain.append(ch);
}

//insertString at any position before the last string in chain
void insertString(String str, String insertbefore){
int theindex = stringchain.indexOf(insertbefore);
stringchain.insert(theindex, str);
theindex += str.length();
stringchain.insert(theindex, spaces);
}

//properties method
int propMethod(char ch){
int resultvar = 0;
for (int i=0; i if(stringchain.charAt(i) == ch ){
resultvar +=1;
}
}
return resultvar;
}


public static void main(String[] args) {
//an instance of our class
BuilderExample build = new BuilderExample();

//on instantiating the string contains only "A"
System.out.println("Initial chain is "+initialchain);

//we're appending the string "Teaching" to the chain
build.appendString("Teaching");
System.out.println(current+BuilderExample.stringchain);

//we'll insert a string at a chosen position
build.insertString("Tremendous", "Teaching");
System.out.println(current+BuilderExample.stringchain);

//let's add "Tool" after "Teaching"
build.appendString("Tool");
System.out.println(current+BuilderExample.stringchain);

//suppose we made a mistake, we didn't insert '!' in "Tool"
build.appendChar('!');
System.out.println(current+BuilderExample.stringchain);

//if we want to know the properties of the string built
System.out.print("There are "+(build.propMethod(' ')+1)+"
words");
System.out.println(" and
+BuilderExample.stringchain.length()+" characters in the chain");
}
}

Enjoy!

SNIPPET, java.lang.StringBuilder

SNIPPET, java.lang.StringBuilder

This class defines a mutable sequence of characters. It was created as a drop-in replacement for StringBuffer class in places where the StringBuffer would be used for single threaded actions.

The principal operations in a StringBuilder are the append and insert methods which are overloaded and accept data of any type. A given datum is effectively converted to a string and the characters of that string inserted or appended to the StringBuilder where the append method add these characters at the end of the builder and the insert method at a specified point.

Here is a simple class, BuilderExample, that is based on the principles of the StringBuilder class.

package transkawa;

class BuilderExample {
static StringBuilder stringchain = new StringBuilder("A");
static final String initialchain = stringchain.toString();
String spaces = " ";
static String current="Current string chain: ";

//to append strings in this class, first attach a space
//then attach the string. Append always at the last position
void appendString(String str){
stringchain.append(spaces);
stringchain.append(str);
}

//this method appends a char without spaces
void appendChar(char ch){
stringchain.append(ch);
}

//insertString at any position before the last string in chain
void insertString(String str, String insertbefore){
int theindex = stringchain.indexOf(insertbefore);
stringchain.insert(theindex, str);
theindex += str.length();
stringchain.insert(theindex, spaces);
}

//properties method
int propMethod(char ch){
int resultvar = 0;
for (int i=0; i if(stringchain.charAt(i) == ch ){
resultvar +=1;
}
}
return resultvar;
}


public static void main(String[] args) {
//an instance of our class
BuilderExample build = new BuilderExample();

//on instantiating the string contains only "A"
System.out.println("Initial chain is "+initialchain);

//we're appending the string "Teaching" to the chain
build.appendString("Teaching");
System.out.println(current+BuilderExample.stringchain);

//we'll insert a string at a chosen position
build.insertString("Tremendous", "Teaching");
System.out.println(current+BuilderExample.stringchain);

//let's add "Tool" after "Teaching"
build.appendString("Tool");
System.out.println(current+BuilderExample.stringchain);

//suppose we made a mistake, we didn't insert '!' in "Tool"
build.appendChar('!');
System.out.println(current+BuilderExample.stringchain);

//if we want to know the properties of the string built
System.out.print("There are "+(build.propMethod(' ')+1)+"
words");
System.out.println(" and
+BuilderExample.stringchain.length()+" characters in the chain");
}
}

Enjoy!

INTERFACES(4)

INTERFACES(4)

ANNOTATIONS
Annotations provide data about a program that is not part of the program itself. They have no direct effect on the operation of the code they annotate.

Annotations have a number of uses, among which are:
1. they provide information for compilers and can be used to detect or suppress warnings.
2. can be used for compiler-time and deployment-time processing. Software tools can process annotations to generate code, XML files and so forth.
3. for runtime processing. Some annotations are available for examination at runtime.

Note that annotations may be used as modifiers in any declaration, whether package, class, interface, field, method, parameter, constructor or local variable.

package examples;

public @interface Author {
String name();
String date();}

//annotation as modifier for class MyClass
//annotations *must* contain an element-value pair for
//every element of the corresponding annotation type
@Author (
name="nnaemeka david",
date="10/04/2007"
)
public class MyClass {}

annotations may also be used on enum constants.

A compile time error is more than one annotation is specified for a declaration.

There are 3 kinds of annotations:
1. normal annotations – these are fully general annotations
2. marker annotations – these are shorthand annotations
3. single-element annotations - these are shorthand annotations

Normal annotations: normal annotations are used to annotate program elements.

Notation: @TypeName (ElementValuePairsopt)

Where ElementValuePairs are notated as: Identifier = ElementValue

And ElementValue is either:
a. a conditional expression
b. an annotation
c. an element value array initialiser which is notated as {ElementValueopt,opt}

example:
public @interface Author {
String name(); //return type of this method defines the element type
//of the element-value pair
}

//here, TypeName is Author; identifier is name, Element
//value conforms to the return type for method name in
//Author annotation, which is String.
@Author(name="nnaemeka david")
public class MyClass {}

the element type T of the element-value pair is commensurate with an element value V if and only if one of the following conditions is true:
1. T is an array type E[] and either
a. V is an ElementValueArrayInitialiser and each ElementValue initialized in V is commensurate with E, or
b. V is an element value that is commensurate with T

2. The type of V is assignment compatible with T and therefore
a. If T is a primitive type or String, V is a constant expression
b. V is not null
c. If T is Class, or an invocation of Class, and V is a class literal
d. If T is an enum type and V is an enum constant.
Element types must always be commensurate with element values.
Little example:

package examples;

public @interface Author {
int[] number();
}

public @interface Author {
int[] number();
}

An annotation on an annotation type declaration is called a meta-annotation.

import java.lang.annotation.*; //these type on demand import necessary
//to use @Document annotation

//a meta-annotation
@Documented
public @interface Author {
int[] number();
}

Marker annotations: marker annotations notated as: @TypeName
are simply shorthands for the normal annotation, @TypeName().

package examples;

import java.lang.annotation.*;

@Documented
public @interface Author {}

//marker annotation
@Author()
public class MyClass {}

Simple-element annotation: this is a shorthand designed for use with single-element annotation types. Note that by convention, single-element annotation types have a single method, value.

The notation for single-element annotation is: @TypeName(ElementValue) which is the shorthand for the normal annotation: @TypeName(value = ElementValue).

package examples;

import java.lang.annotation.*;

@Documented
public @interface Author {
String value();
}

//single-element annotation
@Author("david")
public class MyClass {}

there are lots of examples in section §9.7 that illustrates this three types of annotations.

INTERFACES(3)

INTERFACES(3)

ANNOTATION TYPES
An annotation type declaration is a special type of interface declaration using the at sign @ along with the keyword interface.

Notation:
InterfaceModifiersopt @interface Identifier AnnotationTypeBody

AnnotationTypeBody: {AnnotationTypeElementDeclarationopt}

Where the annotation type element declarations can be one or many and notated as either one or many of:
AbstractMethodModifiersopt Type Identifier() DefaultValueopt;
ConstantDeclaration
ClassDeclaration
InterfaceDeclaration
EnumDeclaration
AnnotationTypeDeclaration
;

The default values are notated thus: default ElementValue

By virtue of its context free syntax, the following restrictions are imposed on annotation type declarations:
1. annotation type declarations cannot be generic
2. no extends clause is permitted (annotation types (denoted with the sign @) implicitly extend annotation.Annotation.)
3. methods cannot have any parameter
4. methods cannot have any type parameter.
5. method declarations cannot have a throws clause.

Take note: unless explicitly modified, all the rules applying to ordinary interface declarations apply to annotation type declarations.

The identifier in an annotation type declaration specifies the annotation type name and it cannot be the same simple name as any of its enclosing classes or interfaces.

If an annotation a on an annotation type declaration corresponds to an annotation type T, and T has a (meta-)annotation m that corresponds to annotation.Target, then m must have an element whose value is annotation.ElementType.ANNOTATION_TYPE or annotation.ElementType.TYPE or a compile time error occurs.

The direct superinterface of an annotation type is always annotation.Annotation.

The return type of a method declared in an annotation type is either:
1. one of the primitive types
2. String
3. Class and any invocation of Class
4. an enum type
5. an annotation type
6. an array of any of the types above,
otherwise a compile time error occurs.

If any method declaration in an annotation type has a signature that is override-equivalent to that of any public or protected method declared in the class Object or in the interface annotation.Annotation, then a compile time error occurs.

Each method declaration in an annotation type declaration defines an element of the annotation type. Annotation types can have zero or more elements which are only those defined by the methods it explicitly declares.

A compile time error for an annotation of type T to contain an element of type T, either directly or indirectly.

An annotation type element may have a default value specified. This is done by following the empty parameter list with the keyword default and then the default value of the element.

An ElementValue is used to specify a default value and must be correctly typed otherwise a compile time error. An ElementValue is always FP-strict.

(see jls for example. No need to duplicate it here. )

By convention, value is the name of the sole element in a single-element annotation type.

Predefined annotation types:
Target: this predefined annotation type is used in meta-annotations to indicate that the kind of program element an annotation type is applicable to.

Target has one element of, annotation.ElementType[]

The meta-annotation below indicates that the declared type is itself a meta-annotation type. It can only be used on annotation type declarations.

@Target (ElementType.ANNOTATION_TYPE)
public @interface MetaAnnotationtype { ... }

the meta-annotation below indicates that the declared type is intended solely for use as a member type in complex annotation type declarations. It cannot be used to annotate anything directly.

@Target ({})
public @interface MemberType { ... }

note: a single ElementType cannot appear more than once in a Target annotation.

Retention: indicates if annotations may be present only in the source code or in the binary form of a class or interface. The annotation type, annotation.Retention is used to choose between the above two.

If an annotation a corresponds to type T and T has a meta-annotation m that corresponds to annotation.Retention, then
- if m has an element whose value is annotation.RetentionPolicy.SOURCE, then a java compiler must ensure that a is not present in the binary representation of the class and interface in which it appears.
- If m has an element with value annotation.RetentionPolicy.CLASS , or annotation.RetentionPolicy.RUNTIME, then a java compiler must ensure that a is represented in the binary representation of the class or interface in which a appears, unless m annotates a local variable declaration, then it won’t be retained in the binary representation.

Inherited: this indicates that annotations on this class are automatically inherited.

Override: this annotation is useful for early detection of programmers mistaking an overload for an override for a method.

If a method declaration is annoted with the annotation @override, but this method does not in fact override any method declared in a superclass, a compile time error will occur.

SuppressWarnings: used to indicate that the named compiler warnings should be suppressed in the annotated element (and in all program elements contained in the annotated element). It contains a single element that is an array of String.

INTERFACES(2)

INTERFACES(2)

INTERFACE MEMBERS:
The members of an interface are:
1. those members declared in the interface
2. members inherited from direct superinterfaces
3. where there is no direct superinterface, then the interface implicitly declares a public abstract member m with signature s return type r and throws clause t corresponding to each public instance method m with signature s return type r and throws clause t declared in Object unless an explicit declaration of a method with the same signature, return type and compatible throws clause exists. If m is declared to be final in Object and the interface explicitly declares me, then a compile time error results.

It is a compile time error if the interface declares a method with a signature that is override-equivalent to a public method of Object, but has a different return type or incompatible throws clause.

Except for those fields, classes and interfaces that is hides and methods it overrides, an interface inherits members of an interface it extends.

FIELD (CONSTANT) DECLARATION:
Constant declaration:

ConstantModifiersopt Type VariableDeclarators;

Where constant modifiers are one of:
Annotation public static final

Note: every field declaration in the body of an interface is implicitly public static final. Redundant modifier specification is allowed.

If an annotation a on a field declaration corresponds to an annotation type T, and T has a (meta-)annotation m that corresponds to annotation.Target, then m must have an element whose value is annotation.ElementType.FIELD, or a compile time error occurs.

A same name field in an interface with its superinterface hides the field of the superinterface provided they are accessible and the field exists.

Although an interface can inherit two fields with the same name, referencing this fields using their simple names will result in compile time error due to ambiguous referencing.

If inheritance of a field can be done through several paths, inheritance is considered to be just once and the field’s simple name can be used to referenced it.

Initialisation of fields in interfaces:
Every field in the body of an interface must have an initialization expression, which need not be a constant expression. When the interface is initialized, the variable initialiser is evaluated and the assignment performed exactly once.

Note:
1. initialization expression for an interface field cannot contain a reference by simple name, a. to itself; or b. to another field whose declaration occurs textually later in the same interface.
2. the keywords this or super cannot occur in the initialization expression for a field of an interface unless this occurrence is within the body of an anonymous class.

(the jls contains some straight-to-the-point examples for the above, at section §9.3)

ABSTRACT METHOD DECLARATION:
Notation:
AbstractMethodModifiersopt TypeParametersopt ResultType MethodDeclarator Throwsopt

Abstract method modifiers can be one of the following:
Annotation public abstract

Modifier appearance redundancy is not allowed.

Every method declaration in an interface body is implicitly abstract, so its body is always represented by a semicolon, ;, and not a block.

Every method declaration in the body of an interface is implicitly public.

Abstract methods cannot be static and vice versa, so member interface methods can never be static.

Annotation rules also apply to interface methods i.e if an annotation a on a method declaration corresponds to an annotation type T, and T has a (meta-)annotation m that corresponds to annotation.Target, then m must have an element whose value is annotation.ElementType.METHOD, or a compile time error occurs.

These are known compile time errors:
1. for an interface to declare two methods with override-equivalent signatures, whether implicitly or explicitly. However, an interface may inherit several methods with such signatures.
2. interface methods must not be declared final although implementing classes can declare its implementation as final
3. interface methods may be generic.

Inheritance and overriding.
If an interface I has an instance method m1 and interface J has an instance method m2, m1 overrides m2 if and only if the following are true:
- I is a subinterface of J
- The signature of m1 is a subsignature of the signature of m2.

Note that overriding and hiding implies return type substitutability along with subtyping on the overriding type which can issue an unchecked warning.

A method declaration does not have a throws clause that conflicts with that of any method it overrides, otherwise, compile time error occurs.

If a type declaration T has a member method m1 and another method m2 exists, declared in T or a supertype of T, a compile time error occurs if all if all the following holds:
1. m1 and m2 have same name
2. m2 is accessible from T
3. the signature of m1 is not a subsignature of the signature of m2
4. m1 or some method m1 overrides (directly or indirectly) has the same erasure as m2 or some method m2 overrides (directly or indirectly.)

notes:
a. methods are overridden on a signature-by-signature basis.
b. All methods not overridden by an interface in the supertype are automatically inherited.
c. An interface can inherit several methods with override-equivalent signatures, however, one of the inherited methods must be return-type substitutable for any other inherited method, otherwise a compile time error occurs.
d. A method can be inherited from several paths, inheritance is considered as being only once.

Overloading: overloading of interface member methods similar to as detailed for class methods overloading.

MEMBER TYPE DECLARATIONS
Interfaces may contain member type declarations; a member type declaration in an interface is implicitly static and public.

A member type C enclosed in an interface N has a fully qualified name N.C.

Member type hiding can occur between an interfaces and its superinterface.

An interface will inherit all non-private accessible non-hidden member types of its superinterface.

An interface can inherit 2 or more type declarations with the same name, but on referencing them with their simple names, ambiguity results.

If the same type declaration is inherited with different paths by an interface, then inheritance is assumed to be but once.

INTERFACES

INTERFACES

An interface declaration introduces new reference types whose members are classes, interfaces, constants and abstract methods. Being without implementation, unrelated classes can implement interfaces by providing a definition for its abstract methods.

There are two kinds of interfaces, normal interfaces and annotation types, and they both can either be top level interfaces or nested interfaces (i.e with their declaration in the body of another class or interface).

Interface Declarations
An interface declaration specifies a new named reference type. There are two kinds of interface declarations:
NormalInterfaceDeclaration
AnnotationTypeDeclaration
A normal interface declaration is notated thus:
InterfaceModifiersopt interface Identifier TypeParameteropt ExtendsInterfacesopt InterfaceBody

Annotation type declarations will be broached later.

The identifier in an interface declaration denotes the name of the interface which name should not be the same as an enclosing class or interface otherwise, a compile time error will result.

Interface Modifiers
The interface declaration may include interface modifiers which may be one of:
public protected private abstract static strictfp

not all modifiers are applicable to all interfaces. Protected and private are applicable only to member interfaces within a directly enclosing class declaration; static applies only to member interfaces; the same modifier should not appear more than once in the same interface declaration.

If an annotation a for an interface declaration corresponds to an annotation type T, and T has a (meta-)annotation m such that m corresponds to annotation.Target, then m must have an element whose value is annotation.ElementType.TYPE, otherwise a compile time error results.

Note that every interface is implicitly abstract, but the use of this modifier is obsolete; a strictfp interface declaration is to make all double and float expressions in the interface be explicitly FP-strict, including nested types declared in the interface.

Generic interfaces and type parameters
Generic interfaces are interfaces which declare one or more type variables which are known as the type parameters of the interface and delimited by angle brackets, ‘<’ and ‘>’. A generic interface declaration defines a set of types, one for each possible invocation of the type parameter section. All type parameters share the same interface at runtime.

The scope of an interface’s type parameter is the entire declaration of the interface including the type parameter section itself. Therefore, type parameters can appear as part of their own bounds, or as bounds of other type parameters declared in the same section.

Never refer to the type parameter of an interface anywhere in a member field or member type of an interface.

Superinterfaces and subinterfaces:
If the extends clause is provided, then the interface being declared extends each of the other named interfaces and therefore inherits the member types, methods and constants of each of the other named interfaces, called the direct superinterfaces of the interface being declared.

If a class implements the declared interface, it is also considered to implement all the interfaces this interface extends.

Notation: extends InterfaceType(s)

Note that interface types can be generic and must be accessible.

An interface I directly depends on a type T if T is mentioned in the extends clause of I either as a superinterface or as a qualifier within a superinterface name.

An interface I depends on a reference type T if any of the following conditions hold:
1. I directly depends on T
2. I directly depends on a class C that depends on T
3. I directly depends on an interface J that depends on T (using this definition recursively.)
An interface cannot directly depend on itself.

While every class is an extension of the Object class, there is no interface such that all interfaces implicitly extends it.

The suerinterface relationship is a transitive closure of the direct superinterface relationship. An interface K is a superinterface of interface I if either of the following is true:
1. K is a direct superinterface of I
2. an interface J exists such that K is an interface of J, and J is a superinterface of I, applying this definition recursively.
Where K is a superinterface of J then J is said to be a subinterface of K.

Interface Body and member declarations: the body of an interface may declare members of the interface where the members are either:
1. a constant declaration
2. an abstract method declaration
3. a class declaration
4. an interface declaration.
The scope of the declaration of a member m declared in or inherited by an interface type I is the entire body of I, including any nested type declarations.

Access to interface member names: all interface members are implicitly public and access to them is allowed if the interface is also declared public or protected.

CLASSES(8)

CLASSES(8)

ENUMS
The notation form for enum type is:
ClassModifiersopt enum Identifier Interfacesopt EnumBody

Where Enum body is:
{ EnumConstantsopt,opt EnumBodyDeclarationsopt }

The body of an enum type may contain enum constants which defines instances of the enum type.

Notes:
1. never explicitly instantiate an enum type
2. enum constants can never be cloned due the the clone method of Enum
3. the special treatment of the serialization mechanism ensures that duplicate instances are never created as a result of deserialisation.
4. reflective instantiation of enum types is prohibited.
Notes 1-4 above ensures that only an enum constant can define instances of enum types.

Enum constants thus have the following notation:
Annotations Identifier Argumentsopt ClassBodyopt
Where Arguments: (ArgumentListopt)

Also the optional enum body declaration is declared thus: ;ClassBodyDeclarationsopt

An enum constant when preceded by annotation modifiers, say a, corresponding to an annotation type T, and T has a (meta-)annotation m such that the m corresponds to annotation.Target, then m must have an element whose value is annotation.ElementType.FIELD, or a compile time error results.

An enum constant may be followed by arguments and these arguments are passed to the constructor of the enum type when the constant is created during class initialization. If the arguments are omitted, an empty argument list is assumed. If the enum type has no constructor declarations, a parameterless default constructor is provided (matching the implicit empty argument list) and the default constructor is private.

The optional class body of an enum constant implicitly defines an anonymous class declaration that extends the enclosing enum type. The class body is governed by the usual anonymous class rules, in particular, it cannot contain constructors.

Compile time error scenarios, brief:
1. a compile time error if an enum type is declared abstract
2. an enum type, E, cannot have abstract methods unless E has one or more enum constants and all these enum constants have class bodies that provide concrete implementations of the abstract method.
3. the class body of an enum constant cannot declare an abstract method.

An enum type is implicitly final unless it contains an enum constant that has a class body, but does not have to be explicitly so defined otherwise compile time error.

Nested enum types are implicitly static and one can explicitly declare them thus.

Any constructor or member declaration declared with an enum declaration applies to the enum type exactly as if they had been present in the class body of a normal class declaration unless explicitly stated otherwise.

The direct superclass of an enum type named E is Enum. in addition to members inherited from Enum, for each declared enum constant n the enum type has an implicitly declared public static final field named n of type E. these fields are considered to be declared in the same order as the corresponding enum constant and initialized to the corresponding enum constant. Each such field is also considered annotated by the same annotations as the corresponding enum constants. The enum constant is said to be created when the corresponding field is initialized.

The following implicitly declared static method exists for any enum type:
public static E[] values(); //this returns an array containing the constants of the enum
type in the order declared.

public static E valueOf(String name); //returns the enum constant with the specified
name

read the specific examples in the jls!

CLASSES(7)

CLASSES(7)

MEMBER TYPE DECLARATIONS
Member classes or member interfaces are nested classes or interfaces. The name of a member type hides any and all accessible declarations of member types with the same name in superclasses and superinterfaces.

If there exists a declaration of a member type in scope before the declaration of another member type with the same name, then these other member type declaration will shadow the earlier one.

If a member class or interface with simple name C is directly enclosed in another class declaration with fully qualified name N, then N.C is the fully qualified name of the member class or interface.

INSTANCE INITIALISERS
An instance initialiser declared in a class is executed when an instance of the class is created.

A named class’ instance initialiser should not throw any exceptions unless the following conditions hold: a. that exception or its supertype must be explicitly declared in the throws clause of the constructor, b. the class must have at least one explicitly declared constructor.

An anonymous class’ instance initialiser can throw any number of exceptions.

An instance initiliser must complete normally.

There must be no return statement in an instance initialiser.

Try to declare instance variables used in instance initialiser before usage even though these instance variable declarations are in scope.

Instance initialisers can refer to the current object this, to any variable that is in scope and can use the keyword super.

STATIC INITIALISERS
Any static initialisers declared in a class are executed when the class is initialized, and together with any field initialisers for class variables, may be used to initialize the class variables of the class.

Notation for static initialisers is: static Block

Static initialisers and class variable initialisers are executed in textual order. Declaration after usage of class variables is discouraged even though the variables may be in scope.

No return statement must appear inside the block of a static initialiser.

The keywords this, super or any type variable declared outside the initialiser are not allowed and produce compile time errors.

CONSTRUCTOR DECLARATIONS
a constructor is used in the creation of an object that is an instance of a class.

Notation:
ConstructorModifiersopt ConstructorDeclarator Throwsopt ConstructorBody

Where the Constructor Declarator is notated thus:
TypeParametersopt SimpleTypeName (FormalParameterListopt)

The simple name of the constructor declarator must be the simple name of the class in which the constructor is declared, otherwise compile time error. Except for the simple name requirement, the constructor looks like a method declaration without any return type.

Very simple example of a constructor:

class Loader {
int x, y;
Loader(){}
}
Constructors are invoked by:
1. class instance creation expressions.
2. conversions and concatenations caused by the string concatenation operator, +.
3. explicit constructor invocations from other constructors.

Access to constructors is governed by access modifiers.

Constructor declarations are not members. They are not inherited and therefore cannot be overridden or hidden.

The formal parameters and formal type parameters of constructors are identical in structure and behaviour to those of a method.

It is a compile time error to declare two constructors whose signatures are override-equivalent or have the same erasure types in a class.

Constructor Modifiers: the choice of constructor modifiers are either one of public, protected or private, and a single one can never be declared twice nor can more than one of the choice above be chosen. If a normal class has a constructor without an access modifier, then the default is chosen. An enum type has default access modifier of private and cannot ever be declared public or protected.

If an annotation a on a constructor corresponds to an annotation type T and T has a meta-annotation m such that m corresponds to annotation.Target, then m must have an element whose value is annotation.ElementType.CONSTRUCTOR, otherwise a compile time error results.

Unlike methods, a constructor cannot be:
a. abstract, because it would not be implemented
b. final, because it is never inherited.
c. Static, because since a constructor is invoked with respect to an object, it makes no sense to declare it static.
d. Synchronized, because it would lock the object under construction, making it unavailable to other threads until all constructors for the object have finished their work.
e. Native, a design decision in java to ensure proper superclass constructor invocations.
f. Strictfp, a design decision to ensure that unlike in method modifiers, the class determines the fp-strictness of the results of the constructor.

Generic constructors: whether or not the class a constructor is in is generic or not, a constructor can be declared generic. A generic constructor must declare one or more type variables known as the formal type parameters of the constructor which form is identical to the type parameter list of a generic class or interface.

The scope of a constructor’s type parameter is the entire declaration itself, including the type parameter section. Type parameters can therefore appear as part of their own bounds or as bounds of other type parameters in the same section.

On invoking a generic constructor, you need not provide the type parameters explicitly, and when not provided, they are inferred.

Constructor throws: identical to that of a method.

The type of a constructor: consists of its signature and exception types given its throws clause.

Constructor body: the first statement of a constructor body may be the explicit invocation of another constructor of the same class or of the direct superclass.

{ExplicitConstructorInvocationopt BlockStatementsopt}

A constructor using this should not directly or indirectly invoke itself, otherwise a compile time error results.

If the constructor is a constructor for an enum type, it is a compile time error for it to invoke the superclass constructor explicitly.

If a constructor does not begin with a. an explicit constructor invocation, b. and the constructor being declared is not part of the primordial class of Object, then the compiler assumes the constructor begins with “super();”, an invocation of the constructor of its direct superclass that takes no arguments.

Except for possible explicit constructor invocations, the body of a constructor is similar to that of a method.

See examples in §8.8.7 of the jls.

Explicit constructor invocations: notations are of this form
1. alternate constructor invocations, beginning with this are used to invoke an alternate constructor for the class and may be prefaced with explicit type arguments.
nonWildTypeopt this(ArgumentListopt);

2. Superclass constructor invocations are either, a. unqualified, or b. qualified.
a. unqualified superclass constructor invocations, begin with super and may be prefaced with explicit type arguments.
nonWildTypeopt super(ArgumentListopt);
b.
Primary.nonWildTypeopt super(ArgumentListopt);

Where nonWildTypes are notated as where the list of reference types are one or many.

package examples;

public class A {
A(){
System.out.println("I am your super man.");
}
}

public class C extends A {
String color;
C(){
this("white"); //call alternate constructor
}

//the alternate constructor
C(String givencolor){
this.color = givencolor;
}
}

class Loader {

public static void main(String[] args) {
//create an instance without arguments and it'll give
//us white.
C newc = new C();
System.out.println("without arguments default color is
"+newc.color);

//creating one with argument, alternate to customise color
C customc = new C("red");
System.out.println("we've chosen to use the color
"+customc.color);

//not that an implicit call to the super is done each
//time the the subclass constructor is invoked.
}
}

Constructor overloading: constructor overloading similar to method overloading.

Default constructor: if a class contains no default constructor, then one is automatically provided that takes no parameters.

If class is Object, then the constructor an empty body, else the default takes no parameters and simply invokes the superclass constructor with no arguments.

A default constructor has no throws clause.

In an enum type, the default constructor is implicitly private. The default constructor is implicitly given the access modifier that is specified for the class!

Preventing instantiation of a class:

A class can prevent code outside of the class declaration from creating instances of the class by:
1. declaring at least one constructor.
2. preventing the creation of an implicit constructor.
3. declaring all constructors to be private.

A public class can likewise prevent the creation of instances outside the package by:
1. declaring at least one constructor
2. preventing the creation of a default constructor with public access.
3. declaring no constructor that is public.

CLASSES(6)

CLASSES(6)

Method throws: a throws clause is used to declare any checked exceptions that can result from the execution of a method or constructor.

The notation is: throws ExceptionTypeList
Where ExceptionTypeList can be one or more and the types are either a class type or a type variable.

Note:
1. the type of exception mentioned in a throws clause must be a subtype of Throwable.
2. any checked exception that will be encountered in the body of a method or constructor must be mentioned in a throws clause in the declaration of the method or constructor.
3. if a throws clause does not contain that exception type, then the compiler will fail to handle the exception and this will result in a compile time error.

Two exceptions that are not checked because declaring their every occurrence would be inconvenient are:
a. exceptions that are represented by subclasses of the class Error.
b. Exceptions that are represented by subclasses of the class, RuntimeException.

if a method declaration n in a class or interface B overrides or hides a method declaration m in A where A is a superclass or superinterface of B. if n has a throws clause that mentions any checked exception types, then m must have a throws clause, and for every checked exception type listed in the throws clause of n, that same exception class or one of its supertypes must exist in the erasure of the throws clause of m; otherwise a compile time error will result.

If there exists a throws clause in n such that no throws clause in an unerased m is a supertype of this throws clause, then an unchecked warning must be issued.

Method body: a method body is a block of code that implements the method, or simply a semicolon indicating the lack of an implementation. Note that the body of a method must be a semicolon, ;, if and only if the method is declared abstract or native.

If an implementation is to be provided for a method declared void, but the implementation requires no executable code, the method body should be written as a block that contains no executable code, {}.

A method declared void must not contain a return statement in its code, a method declared with a return type must have a return statement in its body that returns a value of type return type.

A method that specifies a return type could in some cases not return anything.

Inheritance, overriding, hiding: a class C can inherit from its direct superclasses and superinterfaces (a) all non-private methods (whether abstract or not) of the superclass and superinterface that are public, protected or the default (i.e package-private), (b) in the same package as C, and (c) are neither overridden nor hidden by a declaration in the class.

Overriding (by instance methods): the example below illustrates this.
Note:
1. an instance method does not override a static method.

package examples;

public class A {
void m1(int enter){
System.out.println("A enters with "+enter);
}
}

//C is a subclass of A
public class C extends A{

//both methods have the same signatures, zero parameters
void m1(int enter){
System.out.println("C enters with with "+enter);
}

//to access the overridden method, we use super
void overridden(int enter){
super.m1(enter);
}
}

class Loader {

public static void main(String[] args) {
//let's show overriding of instance methods
C thec = new C();
thec.m1(35);

//the printout will show that C.m1 overrides A.m1
//although C inherits A.m1

//to access the overridden method, let's call the
//method that uses super
thec.overridden(56);
}
}

Hiding (by class methods):
Note:
1. a static method does not hide an instance method otherwise a compile time error.

package examples;

public class A {
static void m1(int enter){
System.out.println("A enters with "+enter);
}
}

public class C extends A{
static void m1(int enter){
System.out.println("C enters with "+enter);
}

//accessing the static method, m1 of A
void overridden(int enter){
super.m1(enter);
}
}

class Loader {

public static void main(String[] args) {
//m1 of A is overridden
C.m1(30);

//we can access A.m1 though these ways
//a. using the qualified name
A.m1(60);

//b. calling the super through method overridden
C thec = new C();
thec.overridden(60);
}
}

Requirements in Overriding and Hiding: 2 requirements are:
1. return type substitutability for the overriding method on the overridden
2. the throws clause should be a subtype of the throws in the overridden method.
3. the access modifier on an overriding or hiding method must provide at least as much access as the overridden method, d4
a. if the overridden method is declared public, then the overriding method must be declared public otherwise a compile time error
b. if the overridden method is declared protected, then the overriding method must be declared protected or public.
c. If the overridden method has default access (package-private), then the overriding method cannot be private.

Overloading: overloading occurs when two methods of a class (whether both are declared, or both are inherited, or one is declared and the other inherited) have the same name but signatures that are not override equivalent.
Note that overriding on methods occurs on a signature-by-signature basis

CLASSES(5)

CLASSES(5)

Method Signature: two methods have the same signature if they have the same name and argument types. Two methods M and N may be said to have the same argument types if the following conditions hold:
- if they have the same number of formal parameters (possibly zero)
- if they have the same number of type parameters (possibly zero)
- if the formal parameters of M are and of N are if it is possible to replace each Bi in N with the As in M and you get a formal parameter list equal to that in M,
then, M and N have the same signatures.

The signature of a method m1 could be said to be the subsignature of a method m2 if either:
- m2 has the same signature as m1
- the signature of m1 is the same as the erasure of the signature of m2.
Note on subsignatures: this feature was incorporated into the java programming language to express a relationship between two signatures although not identical but one can override the other, a good example is allowing a method without generic types to override one with generic types.

it is a compile time error to declare two methods with override-equivalent signatures where override-equivalent signatures operate on two methods m1 and m2 if m1 is a subsignature of m2 or m2 is a subsignature of m1.

Method Modifiers: the method modifiers are:

public protected private abstract static final synchronized native strictfp

notes:
1. the same modifier cannot appear more than once for a method and public protected private have exclusive usage on each other.
2. if a method declaration contains the keyword abstract it cannot contain any of private static final native strictfp or synchronized.
3. if a keyword native is contained in a declaration it cannot contain strictfp any longer.
4. if there is an annotation a on a method declaration that corresponds to an annotation type T, and T has a meta-annotation m such that m corresponds to annotation.Target, then m has an element with value annotation.ElementType.METHOD, or a compile time error results.
5. the other specified above for method modifiers is customary but not a must.

Abstract methods: the abstract modifier introduces a method as a class member, providing its signature, return type and throws clause but providing no implementation for the method. Abstract methods must appear within abstract classes otherwise a compile time error results. An Enum declaration though can contain an abstract method. If an abstract class is to be subclassed, then that subclass must provide an implementation for its abstract methods, otherwise, a compile time error results.

A private method cannot be declared abstract because a private method cannot be implemented from outside the class.

It is an error for a static method to be declared abstract because invocation of such a method through its qualified name will return a compile time error.

It is a compile time error for a final method to be declared abstract because final methods will never allow a subclass to implement this method or any other method because the implementation is finished and perfect.

An abstract class can override another abstract class by providing an abstract method declaration, giving a facility for detailed specification or loosened specification to be attached to that method.

An instance method that is not abstract can be overridden by an abstract method.

Static methods: a method that is declared static is called a class method. A static method cannot be declared abstract. A static method is invoked with reference to the class and not to any particular object. Use of the keywords this or super in referencing a class method will result in compile time error.

On the other hand, a method that is not declared static is called an instance method and is invoked with respect to a particular object, which is the object which the keywords this or super refer to during execution of the method.

Final methods: a method is declared final to prevent subclass overriding or hiding of the method, attempting to do so results in compile time error. A private method and all methods declared within a final class all behave as if they are final because they cannot be overridden.

A final method can never be declared abstract.

Note that final methods on invocation are inlined by the optimizer or machine code generator.

Native methods: a method that is native is implemented in platform-dependent code, typically written in another programming language, typically C, C++, FORTRAN or Assembly language. The body of a native method is given as a semicolon only, indicating that the implementation is omitted, in place of the method’s body or block.

See §8.4.3.4 of the jls for an example.

Strictfp methods: the effect of strictfp modifier in methods is to make sure that all float or double expressions within the method body are FP-strict.

Synchronized methods: a synchronized method acquires a monitor of an object or class before it executes. If the method is a class (static) method, the monitor associated with the Class object for the method’s class is used, else if an instance method, the monitor associated with the this object is used.

Generic methods: a method is generic if it declares one or more type variables, these being the formal type parameters of the method. The form of the formal type parameter list is identical to that of a class or interface.

The scope of a method’s type parameter is the entire declaration of the method, including the type parameter section. Hence, type parameters can appear as part of their own bounds, or as bounds of other type parameters declared in the same section.

Type parameters for methods are almost always inferred on invocation of the method, so they need not be explicitly provided.

Method return type: the return type of a method states whether the method doesn’t return a value, declared as void, or the type of value a method returns, if it returns a value.

Notion of return type substitutability: two methods are return type substitutable is the following conditions hold for both methods return types:
1. if one of the return types is a primitive type, then the second return type is identical to the first.

//return types for both methods identical
int myMethod(){}

int yourMethod(){}

2. if one of the return types is a reference type, then the other is substitutable to the first if it is a subtype of the earlier or can be converted to a subtype of the earlier by an unchecked conversion.

//where Lagos class was declared to extend Nigeria
//these two methods are return type substitutable
Nigeria myMethod(){}

Lagos yourMethod(){}

3. if the erasure of one of the return types is equal to the raw type of the other.
4. if one is void, then the other is void.

(to be continued)

CLASSES(4)

CLASSES(4)

Initialization of fields: a field declaration with a variable initialiser has the semantics of an assignment to the declared variable and,
- if the declaration is for a class variable (i.e not a static field), then the variable initialiser is evaluated and exactly a single-time assignment performed, when the class is initialized. If the evaluation of a variable initialiser for a static field of a named class(or an interface) can complete abruptly with a checked exception, then this is a compile-time error.
- If the declaration is for an instance variable, (i.e a field that is not static,), then the variable initialiser is evaluated and the assignment performed each time an instance of the class is created. If an instance variable initialiser of a named class can throw a checked exception, then there is a compile time error, otherwise that exception or one of its supertypes is explicitly declared in the throws clause of each constructor of its class and the class has at least one explicitly declared constructor.
An instance variable initialiser in an anonymous class can throw any exception.

Initialization of class variables:
a. any reference to the simple name of an instance variable will result in an error in a class variable initialization expression..
b. use of the keyword this or super in a class variable initialization expression will result in an error.
c. Class variables declared final and initialized with compile time constants will always be initialized first, whether in classes or interfaces.
d. A restriction is placed on using a class variable before its textual declaration, whether or not the class variable is in scope.

Initialization of instance variables:
a. initialization expressions for instance variables may refer to the simple names of class variables.
b. The expression may use the keyword this and super .
c. Restrictions exist on the use of an instance variable before its textual declaration.

Restrictions on the use of fields during initialization:
The declaration of a member of a class needs to appear textually before usage only if the member is an instance (respectively static) field of a class that directly encloses it and the following conditions hold:
a. the usage occurs in an instance variable initialiser(respectively static) of the enclosing class or in an instance initialiser (respectively static) of the enclosing class.
b. The usage is not on the leftmost side of an assignment
c. The usage is via a simple name
d. This class is the innermost class enclosing the usage.

Note: take usage to refer to the main method’s class and you’ll understand why following the rule that you should try to textually declare before usage can really save you some grief. If usage was within same class as instance variable, then static modifiers for the variable would be a must requirement.

METHOD DECLARATIONS:
A method declares executable code that can be invoked, passing a fixed number of values as arguments.

The formal notation for method declaration is: MethodHeader MethodBody

We’ll treat MethodHeader first.

The MethodHeader consists of :
MethodModifiersopt TypeParametersopt ResultType MethodDeclarator Throwsopt

The MethodModifiers, TypeParameters and Throws sections will be discussed shortly. The ResultType signifies the type of value that the method returns and this could be void, that means, it doesn’t return any value, or a recognized type.

The MethodDeclarator has the following notation: identifier (FormalParameterListopt)
The identifier is used in a name to refer to a method.

Try to avoid using same names for methods, classes, fields, member classes or interfaces even if they do not result in compile time errors.

Using two methods with the same signatures (name, number of parameters and types of parameters), will result in a compile time error.

Formal Parameters: the formal parameters of a method or constructor, if any, are specified by a list of comma-separated parameter specifiers.

The parameter specifiers have the notation:
VariableModifiers Type VariableDeclaratorId

Taking them one by one, the VariableModifiers are one or both of final and an annotation. The type specifies the allowed type of the arguments for the method and the VariableDeclaratorId could be an identifier or an array of the specified type. The specification here is for a fixed arity parameter or a case where the number of parameters that are allowed are known, finite and specified as to number. Where the number of allowed formal parameters are not specified, the method is said to have a variable arity parameter of the form methodname(Type… id ) where id is either a simple name or an array of the specified type.
A compile time error occurs if two methods or constructors possess the same formal parameters when they have the same identifier or names.

If an annotation a on a formal parameter corresponds to an annotation type T, and T has a (meta-)annotation, m such that m corresponds to annotation.Target, then m must have an element whose value is element.ElementType.PARAMETER, otherwise a compile time error is issued.

When the parameter of a method is declared final, it is a compile time error to attempt to assign the parameter within the body of the method.

Note that on invocation of a method or constructor, the arguments passed to the method initialize newly created parameter variables each of the Type mentioned in the formal parameter of the method and passed as their simple names before usage in the method body. Note that the identifier mentioned as a parameter in the method declaration may be used to refer to the formal parameter in the body of the method.

Never declare parameter names in local variables of a method or as exception parameters of catch clauses in a try statement of the method or parameter. However, if a method contains a nested class declaration, the parameters of the method may be shadowed inside the nested class. Note though that the nested class should be a local class or an anonymous class.

Never use a qualified name to refer to a formal parameter, only simple names.

If a parameter contains a parameter of type float the value of the float should be in the float value set, and if in the extended-exponent value set this should map well to the float value set otherwise a compile time error results. Same goes for parameters of type double.

But where an actual argument expression corresponding to a parameter variable is not FP-strict, during evaluation of the actual argument expression, intermediate values from the extended-exponent-value set can be used, but prior to being passed to the parameter variable par value, these values have to be mapped to the corresponding value set by method invocation conversion.

An example that illustrates other features pertaining this topic:

package examples;

public class MyMethod {
String terms;

//this method returns no value and has fixed arity parameters,
//which are 1 in number.
void simpleMethod(final String builder){
//we'll refer to the arguments passed with the name
//builder and because of final, it can not be assigned
System.out.println("What was passed was a String,
"+builder);
}

//this method has variable arity parameters, which is considered
//to define a String[]. so am querying the length here.
void variablearity(String... somestrings){
System.out.println(somestrings.length+" parameters were
passed.");
}

//this method has no parameters, empty pair therefore in
//parentheses
String noparam(){
return terms;
}
}

class Loader {

public static void main(String[] args) {
MyMethod thema = new MyMethod();

//new variable initiallized on invocation of simpleMethod
//with type String
thema.simpleMethod("foobar");

//on invocations of a variable arity method, you can define
//how much parameters to pass yourself
thema.variablearity("oh boy", "terrific!", "humdrum");
System.out.print("later ");
thema.variablearity("naughty", "ohlolo", "tellme",
"finale");
}
}

(to be continued)

CLASSES(3)

CLASSES(3)

Superinterface: the optional implements clause in a class declaration introduces the names of interfaces that are direct superinterfaces of the class being declared.

Notation: interfaces:
implements InterfaceTypeList
where InterfaceTypeList may be one or many and are denoted by a TypeParameter specification which might be generic i.e TypeDeclSpecific TypeArgumentsopt

Given a class that could possibly be generic (C, n≥0, c≠Object),the direct superinterfaces of that class type are the types given in the implements clause of the declaration of C where C is a generic class declaration i.e (C, n>0), given a parameterized class type C where each T, denoted Ti, for 1≤i≤n, is a type, the direct superinterface of these parameterized class type are all types in the form I where I is a direct superinterface of C and theta is the substitution [F1 := T1, …, Fn := Tn].

Note:
1. each interface must name an accessible interface type
2. if type name is followed by type arguments, it must be invoked as-is, i.e as declared.
3. type arguments can never be wildcard if 2 is true.
4. an interface can not occur in an implements clause more than once.

An interface I is a superinterface of class type C if any of the following is true:
- I is a direct superinterface
- C has some direct superinterface J for which I is a superinterface.
- I is a direct superinterface of the direct superclass of C

(see jls for a simple, beautiful illustration in the section §8.1.5)

A class may not at the same time be a subtype of two interface types which are different invocations of the same generic interface (because they have similar erasures), or an invocation of a generic interface and a raw type naming that same generic interface.

class B implements I //erasure is /I/
class C extends B implements I //erasure /I/, similar to above

therefore, C cannot implement a type erasure twice.

Class body and Member declarations: a class body may contain declaration of members of a class, that is, fields, methods, nested class and interface declarations. A class body may also contain instance initialisers, static initializers, and constructor declarations.

The scope of member declarations in any class, whether explicitly declared or inherited, is the entire body of the class.

On shadowing, see the “Names, scope of a declaration” blog.

CLASS MEMBERS:
The members of a class type are all one of the following:
- members inherited from its direct superclass, except for class Object, which has no direct superclass.
- Members inherited from any direct superinterface.
- Members declared in the class body.

If a member is declared private, it cannot be inherited by subclasses of that class, but where declared as protected or public, other packages other than the one in which it is declared can inherit it.

The types of members of a class are denoted as:
a. for a field, its type
b. for a method, an ordered 3-tuple consisting of:
a. argument types: a list of the types of the arguments to the member method.
b. Return type: a return type of the method member
c. Throws clause: exception types declared in the throws clause of the method member.
Note: constructors, static initialisers and instance initialisers are not members and therefore are not inherited.

(there are fine examples in the jls at section §8.2 that well illustrate this concept.)

FIELD DECLARATORS: the variables of a class type are introduced by field declarations. Field declaration is of the notation:
FieldModifiersopt Type VariableDeclarators ;
Variable declarations can be one or many and are indicated by a variable identifier that could be a simple or qualified name or a name that is an array type. If a field is initialized on being declared, then it is done so with an expression or an appropriate array initialiser.

package examples;

public class AnyClassWithVariable {
//myfirstvar, mysecondvariable, simple named variables
//am sure you can do qualified names easily!!!
int myfirstvar;
float mysecondvar = 0.006453f; //initialised and declared

//an array variable stringer, not initialised
String[] stringer = new String[3];

//another that is initialised
int[] twoshort = {3, 5, 7};
}

Note:
1. a compile time error is reported if the body of a class declaration declares 2 fields with the same name, but methods, types and fields may have the same name since they are used in different context and disambiguated by different lookup.
2. Hiding fields: a field declared in a subclass with the same name as another in a superclass will hide the field in the superclass or superinterface. Hiding here corresponds to resolution mechanism for field name conflicts. In hiding, the 2 fields may have different type.
3. Shadowing fields: declarations of any accessible field in enclosing classes or interfaces, and any local variable, formal method parameter and exception handler parameter with the same names as that field will result in shadowing.
An illustration:

package examples;

public class AnyClassWithVariable {
//myfirstvar, mysecondvariable, simple named variables
//am sure you can do qualified names easily!!!
int myfirstvar;
float mysecondvar = 0.006453f; //initialised and declared

//an array variable stringer, not initialised
String[] stringer = new String[3];

//another that is initialised
int[] twoshort = {3, 5, 7};

//shadowing of mysecondvar, reflected in main of Loader
void shadowMethod(){
float mysecondvar = 0.098765f;
System.out.println(mysecondvar); //sure to shadow
}
}

public class ClassAndVariable extends AnyClassWithVariable {
int myfirstvar = 400;
}

class Loader {

public static void main(String[] args) {
AnyClassWithVariable tester = new AnyClassWithVariable();

//mysecondvar in scope of class declaration
System.out.println("global mysecondvar is:
"+tester.mysecondvar);

//here shadowed in shadowMethod
System.out.print("global mysecondvar is shadowed by
method's mysecondvar: ");
tester.shadowMethod();

//to start to show hiding, we instantiate the subclass
ClassAndVariable test2 = new ClassAndVariable();

//which myfirstvar int field will test2 give us
System.out.println("Of the two myfristvar fields, test2
gives: "+test2.myfirstvar);
System.out.println("which is hiding the uninitialised one,
AnyClassWithVariable.myfristvar.");

//to get this field, use the qualified name within the
//method scope
}
}

Field modifiers: field modifiers are one of the following:

public protected private static final transient volatile

the appearance of a field modifier must be distinct although ordering is not defined, the above order is customary in java programming.

If an annotation a corresponds to an annotation type T, then T has a (meta-)annotation m that corresponds to annotation.Target, then m must have an element whose value is annotation.ElementType.FIELD, or a compile-time error results.

Static fields: if a field is declared static, there exists exactly one incarnation of the field, no matter how many instances (or zero) of the class that may eventually be instantiated. A static field is sometimes called a class variable and is instantiated on class initialization.

A field not declared static (or called a non-static field) is called an instance variable. An instance variable has distinct incarnations for every instance of a class.
(see the example in §8.3.1.1 for class and instance variable distinction. Well explained. )

Final fields: class and instance variables can be declared final.

It is a compile time error if a blank final (a final variable whose declaration lacks an initializer) class variable is not definitely assigned by a static initialiser of the class in which it is declared.

A blank final instance variable must be definitely assigned at the end of every constructor of the class in which it is declared, otherwise, a compile time error results.

Transient fields: variables declared transient will never be part of the persistent state of an object, such that the system service does not save this variable in persistent storage.

Volatile fields: when a variable is accessed by more than one thread with at least one write operation on the variable followed by any number of reads, the java programming language gives the programmer the facility of locking the variable to ensure consistent and reliable updating of the variable. The modifier volatile supplements this locking making sure that the java memory model gives all threads a consistent value for this variable.

(to be continued)

CLASSES(2)

CLASSES(2)

Inner classes and enclosing instances: any class within another class is said to be nested, but a nested class that is not implicitly or explicitly declared static is said to be an inner class.
Examples illustrating rules on inner classes:

package examples;

class ByTheWay {
static int x = 4;
}

class MyOuter {

//nested class declared static
static class NotInnerClass{

//nested non-inner class can declare static members
//freely
static void trialMethod(){}

}

//nested class, not declared static, d4 inner class
//extending ByTheWay makes Inner inherit a static member, note
class InnerClass extends ByTheWay {

//if inner classes are to declare static members, they
//must be constants
static final String candeclare = "declared";

}

//nested member, interface, implicitly static
interface ImplicitStaticMember{

}

}

And here’s another example that deals with enclosing instances and static contexts.

package examples;

class AnotherExample {
String name="david";
//this inner class, MyInner, occurs in a static context
//due to static oldmethod. therefore it's lexically enclosing
//block that of oldmethod and it has no lexically enclosing
//class
static void oldmethod(){
final int m = 6;
class MyInner {
int y = m; //to use m in MyInner, declare it final
}
}

//inner class without a static context and the immediately
//lexically enclosing class of Without in AnotherExample
class Without {
String name="micheal";
}
}

class Loader {

public static void main(String[] args) {
//since the immediately enclosin instance of Without is
//AnotherExample, reflected in the instance creation
//constructor invocation for any object of type, Without.
//the name field exists for both classes
//creator attaches to its local field in scope
//i.e no naming conflict in same variable for inner and
//its enclosing variable
AnotherExample.Without creator = new AnotherExample().new
Without();
System.out.println("creator knows its name which is:
"+creator.name);

//AnotherExample is the 0th lexically enclosing instance
//of itself, i.e associated only with itself.
AnotherExample myself = new AnotherExample();
System.out.println("Associated with myself, i am:
"+myself.name);

}
}

Superclasses and Subclasses: the optional extends clause in a normal class declaration specifies the direct superclass of the current class.

Notation: super:
extends ClassType
a class is said to be a direct subclass of its direct superclass where the direct superclass is the class from whose implementation the implementation of the subclass is derived.

The direct superclass of an enum type E is Enum.

The extends clause must not appear in the definition of the class Object, because Object is a primordial class and has no direct superclass.

Given a class declaration which could possibly be or not be generic, i.e (C, n>0, c≠Object), the direct superclass of the class type is the type given in the extends clause when C is declared else Object becomes the direct superclass.

If C is a generic class declaration (C,n>0), given a parameterized class type C where for each T, i.e Ti, 1≤i≤n, T is a type, the direct superclass is D, where D is the direct superclass of C and theta is the substitution [F1 := T1, …, Fn := Tn].

Notes:
1. the class type must be an accessible, existing class type.
2. the class type must allow subclassing i.e should never be declared final
3. the class type must never name the class Enum or any of its invocations
4. you should always invoke parameterized types correctly, as declared and never invoke a wildcard type variable.

A subclass relationship is a transitive closure of the direct subclass relationship i.e if class A is a subclass of class C, then either of the following is true:
- A is direct subclass of C
- There exists a B such that A is a subclass of B and B is a subclass of C, applying this definition recursively.

A class C directly depends on a type T if T is mentioned as an extends or implements clause of C either as a superclass or superinterface, or as a qualifier of a superclass or superinterface name.

A class C depends on a reference type T if any of the following are true:
- C directly depends on T
- C directly depends on an interface I that depends on T
- C directly depends on a class D that depends on T.
Note: a class cannot depend on itself.

(to be continued)

CLASSES

CLASSES
Class declarations define new reference types and describe their implementation. This chapter dwells on members of a class, class semantics as well as meanings of access modifiers applied to classes and members of classes.

Class declarations: a class declaration defines new reference types. A class declaration can be either a normal class declaration or an enum declaration.
The notation for a normal class declaration is as below:
ClassModifiersopt class identifier TypeParametersopt Superopt Interfacesopt ClassBody

A class declaration is introduced by the keyword class which can be preceded by an optional access modifier. The identifier in a class declaration specifies the name of a class. We’ve discussed names and meaning of names in an earlier blog. If a class declaration has TypeParameters specified, which is optional, then it is a generic class and in a class declaration, only one optional superclass can exist while any number of interfaces, also optional, can be implemented. The ClassBody is enclosed in opening ‘{‘ and closing ‘}’ wherein the codes for class behaviour and storage spaces are defined.

Class Modifiers: more than one class modifier can be specified for a class. The modifiers that can be attached to class declarations are:

public (applied only to top level classes and member classes. )
protected (applies only to member classes)
private (applies only to member classes)
abstract
static (applies to member classes)
final
strictfp

please note that a compile time error will occur if the same modifier appears more than once in a class declaration. If an annotation on a class declaration, a, corresponds to an annotation type, T and T has a (meta-)annotation m such that m corresponds to annotation.Target, then m must have an element whose value is annotation.ElementType.TYPE or a compile time error occurs.

Abstract classes: an abstract class is a class that is considered incomplete. Note that only a class declared abstract is allowed to have abstract methods, otherwise, a compile time error occurs.

Enum types (in a later blog, please) must not be declared abstract, otherwise, a compile time error occurs. An Enum type is only allowed to declare a method as abstract if it has one or more enum constants with class bodies that provide concrete implementation of the abstract method.

A class C can have abstract methods from any of the 3 ways:
- if C explicitly declares an abstract method (remember, from what we discussed, to do this C has to be abstract itself.)
- if any of C’s superclasses have an abstract method and C neither declares nor inherits a method that implements this method.
- a direct superinterface of C declares or inherits a method (interface are necessarily abstract; to be discussed later) and C neither declares nor inherits the method that implements it.

The example in the jls will be restated here, not for redundancy’s sake but to clarify some points explained therein.

package examples;

//Point is declared abstract because it contains
//an abstract method, alert()
abstract class Point {
int x=1, y=1;
void move(int dx, int dy){
x += dx;
y += dy;
alert();
}
abstract void alert();
}

//ColoredPoint must be declared abstract since it
//inherits alert() from Point and doesn't implement it
abstract class ColoredPoint extends Point {
int color;
}

//SimplePoint although subclass of Point is not abstract
//because it implements alert()
class SimplePoint extends Point{
void alert(){
System.out.print("X is now: "+this.x+". ");
System.out.println("Y is now: "+this.y);
}
}

class Loader {

public static void main(String[] args) {
Point p = new SimplePoint();

//field initialisers and methods of Point can
//now be invoked. try it and see.
p.move(2, 2);
}
}

A class is declared abstract with the intent that subclasses can be created to complete the implementation but where one wants to create a class that needs not be instantiated, a better way to do this is to declare the class’ constructor as private, never invoke the constructor, declare it without arguments and declare no other constructor.
Final classes: a final class is a class whose definition is complete and no subclasses are desired or required for it.
Note:
1. a final class can be a superclass of another class
2. a class declared final can never be overridden because it doesn’t have subclasses
3. a class declared final can never be declared abstract

strictfp classes: the effect of modifying a class with the strictfp modifier is to make all float or double expressions within the class declaration to be explicitly FP-strict i.e strictly within the floating-point value set.

Generic Class and Type Parameters: a class is generic if it declares one or more type variables. These type variables are known as the type parameters of the class.
The type parameter section follows the class name and its delimited by angle brackets, ‘<’ and ‘>’. Note that the type parameters are sectioned in the type and their definition is within the generic class declaration. They share the same class at run-time.

Note:
1. generic classes do not throw exceptions i.e they can never be direct or indirect subclasses of the class Throwable.
2. the scope of a class’ type parameter is the entire declaration of the class including the type parameters section itself. Therefore, type parameters can appear as parts of their own bounds, and as bounds of other type parameters declared in the same section.
3. parameterized class declarations can be nested inside other declarations.

I tried to write a little example to this effect.

package examples;

public class Nigeria {
String name, gmt;
}

public class Ghana {
String name, gmt;
}

public class Africa {
//note: the field declaration for this class will be
//within the scope of the type variables
String name, gmt;
Africa(String countryname, String countrygmt){
this.name = countryname; //type has fields in scope
this.gmt = countrygmt;
}
}

class Loader {

public static void main(String[] args) {
Africa naija = new Africa("Nigeria",
"+1");
Africa kwama = new Africa("Ghana", "0");

//the sections in our generic class share same run-time
//class.
boolean b = naija.getClass()== kwama.getClass();
System.out.println(b);

//let's create a nigerian object
Nigeria mortar = new Nigeria();

//type variable Nigeria not same as class type Nigeria,note
System.out.println("Is type variable same as class type?
"+mortar.equals(naija));

//but class type can reference type variable
mortar.name = naija.name;
System.out.println("Mortar took a name which is: "
+mortar.name);

//we're certain now that we have the right name
System.out.println("In a section of africa there is a
country called: "+naija.name);
}
}

(to be continued)

PACKAGES (3)

PACKAGES (3)

TOP LEVEL TYPE DECLARATIONS:
Top level type declarations declare a top level class type or a top level interface type.

Accessibility: the default accessibility (package-private) applies to this declaration, but if the declaration is public, access is granted to the type by codes from other packages.

Scope: the scope of this declaration is all type declarations in the package in which the top level type is declared.

For instance, where the package has name P and the type is named T, therefore , the fully qualified name is P.T, otherwise the fully qualified name is T, i.e where the type is in an unnamed package.

Note:
1. a restriction can always be enforced by a host system that if a type is not associated with a type name plus an extension (.java or .jav) and either:
a. the type is referred to by code in other compilation units of the package in which the type is declared
b. or the type is declared public (quite sure this’ your piece of cake!)
is true, then the host system should return a compile time error. So, there must be at most one such type per compilation unit.

In a database storage, this restriction might not be imposed.

2. a compile time error occurs if the name of a top level type appears as the name of any other top level class or interface type declared in the same package.

3. also, if (2) is also declared as a type by a single-type-import declaration in the compilation unit containing the type declaration, a compile time error occurs.
Please, see the examples in §7.6 of the jls; they are very instructive and I don’t want to create a redundancy.

UNIQUE PACKAGE NAMES:
Unique package names are essentially necessary when a package is not for local or casual usage but to be widely distributed for easy and automatic installation and cataloguing of packages.

Suggestions of usage:
1. unique package names are usually formed form internet domain names of the organization one belongs to. Example: if your internet domain is mydomain.com, these are usually used to derive unique package names. You reverse this name, component by component to obtain, com.mydomain and use this as a prefix for your package names. Usally, a convention is developed within organizations on how to administer package names using this domain name as base.

Where the internet domain name is not a valid package name for your case you can do the following:
a. where the domain name contains a hyphen or any other special character not allowed in an identifier, convert it into an underscore _ .
b. if any resulting package name components are keywords, then append an underscore to them.
c. If any of the resulting package name components start with a digit, or any other character not allowed as an initial character of an identifier, have an underscore prefixed to the component.

2. the first component of unique package names is always written in all lower-case ASCII letters and should be a top level domain name (currently com, edu, mil, net and org) or one of the English two-letter codes identifying countries as specified in ISO standard 3166, 1981.
com.mydomain.myjavafiles.me
edu.myschool.myschoolfiles._us

3. the name of a package is not meant to imply where the package is stored within the internet. The suggested convention above merely a convenience to piggyback a package naming convention on top of an existing, widely known unique name registry instead of having to create a separate registry for package names.

PACKAGES(2)

PACKAGES(2)

IMPORT DECLARATIONS:
An import declaration allows a static member (in another type) or a named type (in another package) to be referred to by a simple name that consists of a single identifier. The appropriate word, import, is used in the declaration.
There are four types of import declarations:
1. single-type-import declaration (imports a single named type by mentioning its canonical name.)
2. type-import-on-demand declaration (imports all the accessible types of a named type as needed.)
3. single-static-import declaration (imports all accessible static members with a given name from a type, by giving its canonical name.)
4. static-import-on-demand declaration (imports all accessible static members of a named type as needed.)

the scope of any type imported is all the class and interface type declaration in the compilation unit in which the import declaration appears. It does not include, in its scope:
1. the package statement
2. other import declarations in the current compilation unit
3. other compilation units in the same package.

Single-type-import declaration: a single-type-import declaration imports a single type by giving its canonical name, making it available under a simple name in the class and interface declaration in the compilation unit in which the single-type-import declaration appears.

Denoted in this : import TypeName ;
Given a single-type-import declaration, d, the type imported, n, in a compilation unit, c, of package , p, shadows:
- any top level same-named type, d, in another compilation unit of p throughout c.
- any type with same name, n, imported by a type-import-on-demand declaration in c throughout c.
- any type with same name, n, imported by a static-import-on-demand declaration in c throughout c.

Type-import-on-demand declaration: a type import-on-demand declaration allows all accessible types declared in the type or package named by a canonical name to be imported as needed.

Denoted as: import PackageOrTypeName.* ;

Note:
1. the type or package must be accessible or a compile time error is the result.
2. when redundancy in importing is encountered, i.e where 2 or more type import-on-demand declaration names the same type or package, the effect is as if that type were imported only once.
3. if a type-import-on demand declaration and a static-import-on-demand declaration both import the same type in a compilation unit, the effect is as if the static member type of that type were imported only once.
4. a type import on demand declaration will never shadow any other declaration.
Considering a type imported as: import java.util.* ; into the class or interface type of this compilation unit,
5. a simple name Vector refers to a type Vector in java.util.Vector, provided Vector is a. not shadowed, b. obscured in its scope.
6. a single-type-import declaration with simple name Vector might shadow, java.util.Vector; an explicit declaration of a type Vector in the class or interface might shadow java.util.Vector; a nested class or interface with simple name Vector might also shadow it.
7. declaration of a field, parameter or local variable named Vector might obscure java.util.Vector.

Single static import declaration: a single-static-import declaration imports all accessible static members with a given simple name from a type.

Denoted as: import static TypeName.identifier;

The TypeName must be the canonical name of a class or interface type which exists and is accessible, otherwise a compile time error is the result.

The identifier must name at least one existing static member of the named type which is accessible, otherwise a compile time error occurs.
Note:

1. a static member, n, whether field or method name imported this way will shadow every other static-import-on-demand member n whether field or method with the same signature as the single static member.

2. any static type with the same name n imported by a static-import-on-demand declaration is also shadowed i.e
o any static type with same name n imported by static-import-on-demand declaration throughout the compilation unit.
o Any top level type named n declared in another compilation unit throughout the compilation unit
o Any type named n imported in a type import on demand declaration in the compilation unit throughout the compilation unit.

3. redundancy is allowed.

4. if the simple name of a member and a type imported by a single-static-import declaration and a single-type-import declaration respectively, a compile time error occurs.

5. if a single-static-import declaration imports a type n and the compilation unit explicitly declares same type n, a compile time error results.

Static import on demand declaration: a static-import-on-demand declaration allows all accessible type members declared in the type named by a canonical name to be imported as needed.

Denoted as: import static TypeName.* ;
Note:

1. the type used for importing must exist.

2. redundancy is allowed, either in types or members.

3. if a compilation unit contains a static-import-on-demand declaration and a type-import-on-demand declaration that name the same type, the effect is as if the static member types of that type were imported only once.

Automatic imports: all the public type names declared in the predefined package, java.lang are automatically imported.

PACKAGES

PACKAGES

Programs are organized as set of packages, with each package having its own set of names for types, which will help prevent name conflicts. We know by now that if a type is top level and declared public it is generally accessible outside the package. The sections below discusses other features of packages.

Package Members: package members are:
1. subpackages
2. all top level class types
3. top level interface types
where 2 and 3 are declared in all the compilation units of the package.
Note:
a. if a package P has a subpackage Q, then the fully qualified name of the subpackage is P.Q
b. a package may not contain 2 members of the same name or a compile-time error results.
c. The hierarchical naming structure for packages is intended for convenience in related-packages organization but has no significance except to prevent package members from being same name.

Host support for packages:

Each host determines how packages, compilation units and subpackages are created and started, and which compilation units are observed in a particular compilation.

Compilation unit observability in turn determines which packages are observable and which packages are in scope.

Packages may be stored in a local file system or use a distributed file system or some form of database to store source and/or binary code.

Storing packages in a file system: imagine that a directory is used to store the packages that are used for a project, then each immediate subdirectory of the directory would represents a top level package i.e one whose fully qualified name consists of a single simple name.

e.g subdirectories might be java or com or one you created yourself, like api_package. The directory java might contain, amongst others, the subdirectories applet, awt, io, lang or util. these subdirectories then correspond to the packages java.applet; java.awt; java.io; java.lang; java.util which are defined as part of the java API.

Inside the util directory, we might get the following files:
BitSet.java, BitSet.class where the .java files contain the source code and the .class files contain the binary compiled files for a compilation unit that defines the class or interface.

So if we had something like: java.util.BitSet, then the directory structure in same a Windows file system will be java\util\BitSet i.e each package is said to have a top level directory where it is the subdirectory.

If a package name component or class name contains characters outside the allowed ranges (usually ASCII) of an Operating System’s directory naming scheme, the character outside the range can be escaped using the @ character followed by four hexadecimal digits giving the numeric value of the character, similar to the \uxxxx escape we earlier encountered in Unicode escaping.

Supposing we have a package name like this: children.activities.craft.papierM\u00e2ch\u00e9

which in Unicode will give us:
children.activities.craft.papierMâché

and this might be mapped to the directory name:
children\activities\craft\papierM@00e2ch@00e9 in Windows.

Note: if the @ character is not a valid character in a file name for some given host file system, then some other character that is not identifier-valid could be used instead.

Storing packages in a database:

When a host system stores programs, their compilation units and subpackages in a database, such a database must relax some restrictions on compilation units as found in file-based implementation, but provision should exist so that such a program can be exported to file-based implementation.

COMPILATION UNITS

A compilation unit is the goal symbol for the syntactic grammar of java. Note here that type dependence can be created amongst different compilation units i.e where a type contains another type as its member and that other type contains this type as its member.

A compilation unit consists of three parts, each of which is optional:

1. a package declaration, giving the fully qualified name of the package to which the compilation unit belongs. If there is no package declaration, then the package is an unnamed package.

2. import declaration that allows simple names use of types, given other packages and static members of types to be referred.

3. top level type declarations of class and interface types.

A host system determines which compilation units are observable but all compilation units of the package java and its subpackages java.lang and java.io must always be observable. The observability of a compilation unit affects the observability of the package.

Named Packages: a named package is one with a package declaration. A package declaration is defined thus:
Annotationsopt package PackageName ;

The keyword package may optionally be preceded by annotation modifiers. If an annotation a on a package declaration corresponds to an annotation type T, T has a (meta)annotation m that corresponds to annotation.Target, then m must have an element whose value is annotation.ElementType.PACKAGE, otherwise a compile time error occurs.

The PackageName in a package declaration must be the fully qualified name of the package.

Package annotations: annotations may be used on package declaration with the restriction that at most one annotated package declaration is permitted for a given package.

Unnamed Packages: a compilation unit where there is not package declaration is unnamed. Unnamed packages do not have subpackages.

Observability of a package: a package is observable if and only if either:
- a compilation unit containing a declaration of the package is observable.
- A subpackage of the package is observable.

Scope of a package declaration: provided that a package declaration is observable, the scope is all observable compilation units. Subpackage declarations are never in scope. Package declarations never shadow other declarations.