Laborator 10

Download as docx, pdf, or txt
Download as docx, pdf, or txt
You are on page 1of 13

RTTI Run-Time Type Identification

1. Class.forName
package laborator10;
class Candy {
static { System.out.println("Loading Candy"); }
}
class Gum {
static { System.out.println("Loading Gum"); }
}
class Cookie {
static { System.out.println("Loading Cookie"); }
}
public class SweetShop {
public static void main(String[] args) {
System.out.println("inside main");
new Candy();
System.out.println("After creating Candy");
try {
Class.forName("Gum");
//Class c = Class.forName("laborator10.Gum"); //- nu va da exceptie
//putem folosi obiectul class pentru a accesa elemente ale clasei
//c.getFields();
//returneaza o referinta de tip Class
//fara a fi necesara instantierea clasei respetive
} catch(ClassNotFoundException e) {
System.out.println("Couldnt find Gum");
// daca in loc de argumentul Gum vom pune intreg classpath-ul
//cu tot cu package vom obtine referinta catre Class loader-ul clasei Gum
}
System.out.println("After Class.forName(\"Gum\")");
new Cookie();
System.out.println("After creating Cookie");
}
}

2. Metodele obiectului class


package laborator10;
interface HasBatteries {}
interface Waterproof {}
interface Shoots {}
class Toy {
// Comment out the following default constructor

// to see NoSuchMethodError from (*1*)


Toy() {}
Toy(int i) {}
}

class FancyToy extends Toy implements HasBatteries, Waterproof, Shoots {


FancyToy() { super(1); }
}
public class ToyTest {
static void printInfo(Class cc) {
//informatii legate de identificatorul clasei
System.out.println("Class name: " + cc.getName() + " is interface? [" +
cc.isInterface() + "]");
System.out.println("Simple name: " + cc.getSimpleName());
System.out.println("Canonical name : " + cc.getCanonicalName());
}
public static void main(String[] args) {
Class c = null;
try {
//!!!atentie la package-ul in care se afla clasa fancyToy
c = Class.forName("laborator10.FancyToy");//referinta class prin
forName
} catch(ClassNotFoundException e) {
System.out.println("Cant find FancyToy");
System.exit(1);
}
printInfo(c);
for(Class face : c.getInterfaces()) //informatii despre interfetele
implementate de clasa
printInfo(face);
Class up = c.getSuperclass();//referinta de tip class catre clasa de baza
Object obj = null;
try {
// Requires default constructor:
obj = up.newInstance(); //returneaza o instanta a clasei de baza
//utilizand referinta up care este de tip class
} catch(InstantiationException e) {
System.out.println("Cannot instantiate");
System.exit(1);
} catch(IllegalAccessException e) {
System.out.println("Cannot access");
System.exit(1);
}
printInfo(obj.getClass());//getClass se aplica unei instante
//si returneaza o referinta Class la clasa din care face parte obiectul
}
}

3. Initializarea obiectului Class

package laborator10;
import java.util.*;
class Initable {
static final int staticFinal = 47;
static final int staticFinal2 = ClassInitialization.rand.nextInt(1000);
static {
System.out.println("Initializing Initable");
}
}
class Initable2 {
static int staticNonFinal = 147;
static {
System.out.println("Initializing Initable2");
}
}
class Initable3 {
static int staticNonFinal = 74;
static {
System.out.println("Initializing Initable3");
}
}
public class ClassInitialization {
public static Random rand = new Random(47);
public static void main(String[] args) throws Exception {
Class initable = Initable.class; //obtinere referinta de tip Class pentru
Initable
//obtinerea unei referinte Class nu declanseaza initializarea
System.out.println("After creating Initable ref");
//primul acces al unui membru static(atribut sau metoda) provoaca initializarea
System.out.println(Initable.staticFinal);
// Does trigger initialization:
System.out.println(Initable.staticFinal2);
// Does trigger initialization:
System.out.println(Initable2.staticNonFinal);
//Class.forName - asigura initializarea clasei
//atentie la package-ul corect
Class initable3 = Class.forName("laborator10.Initable3");
System.out.println("After creating Initable3 ref");
System.out.println(Initable3.staticNonFinal);
}
}

4. Generic Class reference


package laborator10;
public class GenericClassReference {
public static void main(String[] args) {
Class intClass = int.class; //referinta generica a clasei Integer
Class<Integer> genericIntClass = int.class;

genericIntClass = Integer.class; // Same thing


intClass = double.class;
//Class<Number> genericNumberClass = int.class;
// genericIntClass = double.class; // Illegal
}
}

5. Creati o clasa Individual si salvati-o in package-ul laborator10.pets. Clasa


Individual implementeaza interfata Comparable<Individual>. Clasa
Individual are un contor care permite numararea obiectelor create din
aceasta clasa si un camp membru (constant) id care va salva numarul de
ordine al fiecarui obiect creat din aceasta clasa. Clasa agrega o data
privata nume de tip String. Creati constructor care initializeaza numele cu
argumentul primit la construire, constructor implicit care nu face nimic,
metoda id() care returneaza id-ul obiectului, metoda .toString care
returneaza numele agregat, metoda equals care compara 2 obiecte de tip
Individual (de fapt trebuie sa compare daca numele sunt identice), metoda
compareTo care compara 2 indivizi in ordine lexicografica a numelui.

6. Pets
class Individual{
Individual(){}
Individual(String name ){}
}
class Person extends Individual {
public Person(String name) { super(name); }
} ///:~
class Pet extends Individual {
public Pet(String name) { super(name); }
public Pet() { super(); }
} ///:~
class Dog extends Pet {
public Dog(String name) { super(name); }
public Dog() { super(); }
} ///:~
class Mutt extends Dog {
public Mutt(String name) { super(name); }
public Mutt() { super(); }
} ///:~
class Pug extends Dog {
public Pug(String name) { super(name); }
public Pug() { super(); }
} ///:~
class Cat extends Pet {
public Cat(String name) { super(name); }
public Cat() { super(); }

} ///:
class EgyptianMau extends Cat {
public EgyptianMau(String name) { super(name); }
public EgyptianMau() { super(); }
} ///:~
class Manx extends Cat {
public Manx(String name) { super(name); }
public Manx() { super(); }
} ///:~
class Cymric extends Manx {
public Cymric(String name) { super(name); }
public Cymric() { super(); }
} ///:~
class Rodent extends Pet {
public Rodent(String name) { super(name); }
public Rodent() { super(); }
} ///:~
class Rat extends Rodent {
public Rat(String name) { super(name); }
public Rat() { super(); }
} ///:~
class Mouse extends Rodent {
public Mouse(String name) { super(name); }
public Mouse() { super(); }
} ///:~
class Hamster extends Rodent {
public Hamster(String name) { super(name); }
public Hamster() { super(); }
} ///:~ ~
abstract class PetCreator {
private Random rand = new Random(47);
// The List of the different types of Pet to create:
//lista de tipuri derivate din clasa Pet
public abstract List<Class<? extends Pet>> types();
public Pet randomPet() { // Create one random Pet
int n = rand.nextInt(types().size());
try {
//instantiere obiect de tip Pet
return types().get(n).newInstance();
} catch(InstantiationException e) {
throw new RuntimeException(e);
} catch(IllegalAccessException e) {
throw new RuntimeException(e);
}
}
public Pet[] createArray(int size) {
//creare vector de obiecte derivate din Pet
Pet[] result = new Pet[size];
for(int i = 0; i < size; i++)
result[i] = randomPet();
return result;

}
//creare de ArrayList de obiecte din ierarhia Pet
public ArrayList<Pet> arrayList(int size) {
ArrayList<Pet> result = new ArrayList<Pet>();
Collections.addAll(result, createArray(size));
return result;
}
} ///:~
class ForNameCreator extends PetCreator {
//liste generica ce contine referinte Class ale claselor derivate din Pet
//redefinire deoarece in petCreator atributul types este abstract
private static List<Class<? extends Pet>> types = new ArrayList<Class<?
extends Pet>>();
// Types that you want to be randomly created:
//tipurile din care se vor genera obiecte in mod aleator
private static String[] typeNames = {
"laborator10.Mutt",
"laborator10.Pug",
"laborator10.EgyptianMau",
"laborator10.Manx",
"laborator10.Rat",
"laborator10.Mouse",
"laborator10.Hamster"
};
@SuppressWarnings("unchecked")
private static void loader() {
try {
//adaugarea de referinte class la lista types din fiecare tip de obiect specificat
//in types
for(String name : typeNames)
types.add((Class<? extends Pet>)Class.forName(name));
} catch(ClassNotFoundException e) {
throw new RuntimeException(e);
}
}
static { loader(); } //bloc static de initializare
public List<Class<? extends Pet>> types() {return types;}
}
public class PetCount {
//Hashmap<String, Integer> - colectie in care indicele e string iar
// valoarea este un intreg: ex. V["nr"]=2, V["intreg"]=8
static class PetCounter extends HashMap<String,Integer> {
public void count(String type) {
Integer quantity = get(type);
if(quantity == null)
put(type, 1);
else
put(type, quantity + 1);
}
}

public static void countPets(PetCreator creator) {


PetCounter counter= new PetCounter();
for(Pet pet : creator.createArray(20)) {
// List each individual pet:
//determinarea tipului fiecarui obiect
//cu operatorul instanceof
System.out.println(pet.getClass().getSimpleName() + " ");
if(pet instanceof Pet)
counter.count("Pet");
if(pet instanceof Dog)
counter.count("Dog");
if(pet instanceof Mutt)
counter.count("Mutt");
if(pet instanceof Pug)
counter.count("Pug");
if(pet instanceof Cat)
counter.count("Cat");
if(pet instanceof Manx)
counter.count("EgyptianMau");
if(pet instanceof Manx)
counter.count("Manx");
if(pet instanceof Manx)
counter.count("Manx");
if(pet instanceof Rodent)
counter.count("Rodent");
if(pet instanceof Rat)
counter.count("Rat");
if(pet instanceof Mouse)
counter.count("Mouse");
if(pet instanceof Hamster)
counter.count("Hamster");
}
// Show the counts:
System.out.println(counter);
}
public static void main(String[] args) {
countPets(new ForNameCreator());
}
}

7. Realizati o re-implementare a lui PetCreator utilizat class literals


package laborator10;
import java.util.*;
public class LiteralPetCreator extends PetCreator {
// No try block needed.
@SuppressWarnings("unchecked")
//referinte Class catre toate clasele
public static final List<Class<? extends Pet>> allTypes =
Collections.unmodifiableList(Arrays.asList(

Pet.class, Dog.class, Cat.class, Rodent.class,


Mutt.class, Pug.class, EgyptianMau.class,
Manx.class, Rat.class, Mouse.class,Hamster.class));
// Types for random creation:
private static final List<Class<? extends Pet>> types =
allTypes.subList(allTypes.indexOf(Mutt.class), allTypes.size());
public List<Class<? extends Pet>> types() {
return types;
}
public static void main(String[] args) {
System.out.println(types);
}
}

package laborator10;
import java.util.ArrayList;
public class Pets {
public static final PetCreator creator = new LiteralPetCreator();
public static Pet randomPet() {
return creator.randomPet();
}
public static Pet[] createArray(int size) {
return creator.createArray(size);
}
public static ArrayList<Pet> arrayList(int size) {
return creator.arrayList(size);
}
}

package laborator10;
public class PetCount2 {
public static void main(String[] args) {
PetCount.countPets(Pets.creator);
}
}
package laborator10;
import java.util.*;
public class TypeCounter extends HashMap<Class<?>,Integer>{
private Class<?> baseType; //referinta generica de tip Class
public TypeCounter(Class<?> baseType) {
this.baseType = baseType;
}
public void count(Object obj) {
Class<?> type = obj.getClass();
if(!baseType.isAssignableFrom(type))
throw new RuntimeException(obj + " incorrect type: "
+ type + ", should be type or subtype of " +

baseType);
countClass(type);
}
private void countClass(Class<?> type) {
Integer quantity = get(type);
put(type, quantity == null ? 1 : quantity + 1);
Class<?> superClass = type.getSuperclass();
if(superClass != null && baseType.isAssignableFrom(superClass))
countClass(superClass);
}
public String toString() {
StringBuilder result = new StringBuilder("{");
for(Map.Entry<Class<?>,Integer> pair : entrySet()) {
result.append(pair.getKey().getSimpleName());
result.append("=");
result.append(pair.getValue());
result.append(", ");
}
result.delete(result.length()-2, result.length());
result.append("}");
return result.toString();
}
}
package laborator10;
public class PetCount4 {
public static void main(String[] args) {
TypeCounter counter = new TypeCounter(Pet.class);
for(Pet pet : Pets.createArray(20)) {
System.out.println(pet.getClass().getSimpleName() + " ");
counter.count(pet);
}
System.out.println(counter);
}
}

8. Diferenta dintre instanceof si compararea obiectelor de tip Class


package laborator10;
class Base {}
class Derived extends Base {}
public class FamilyVSExactType {
static void test(Object x) {
//determinarea tipului unui obiect
System.out.println("Testing x of type " + x.getClass());
//testarea cu instance of - daca un obiect este de un anumit tip
System.out.println("x instanceof Base " + (x instanceof Base));
System.out.println("x instanceof Derived "+ (x instanceof Derived));
//testarea daca o referinta este o instanta a unei clase sau nu
//(testeaza daca obiectul a fost construit sau nu)

System.out.println("Base.isInstance(x) "+ Base.class.isInstance(x));


System.out.println("Derived.isInstance(x) " + Derived.class.isInstance(x));
//compararea intre tipuri: x are acelasi tip ca si clasa.class
System.out.println("x.getClass() == Base.class " + (x.getClass() ==
Base.class));
System.out.println("x.getClass() == Derived.class " + (x.getClass() ==
Derived.class));
System.out.println("x.getClass().equals(Base.class)) "+
(x.getClass().equals(Base.class)));
System.out.println("x.getClass().equals(Derived.class)) " +
(x.getClass().equals(Derived.class)));
}
public static void main(String[] args) {
test(new Base());
test(new Derived());
}
}

9. Extragerea metodelor unei clase (care indeplinesc o anume


conditie)
package laborator10
import java.lang.reflect.*;
import java.util.regex.*;
public class ShowMethods {
private static String usage ="usage:\n" +
"ShowMethods qualified.class.name\n" +
"To show all methods in class or:\n" +
"ShowMethods qualified.class.name word\n" +
"To search for methods involving word";
private static Pattern p = Pattern.compile("\\w+\\.");
public static void main(String[] args) {
if(args.length < 1) {
System.out.println(usage);
System.exit(0);
}
int lines = 0;
try {
//referinta Class
Class<?> c = Class.forName(args[0]);
//colectia metodelor din clasa
Method[] methods = c.getMethods();
//constructorii claselor
Constructor[] ctors = c.getConstructors();
if(args.length == 1) {
//iterarea metodelor din clasa
for(Method method : methods)
System.out.println(p.matcher(method.toString()).replaceAll(""));
//iterarea constructorilor in clasa
for(Constructor ctor : ctors)

System.out.println(p.matcher(ctor.toString()).replaceAll(""));
lines = methods.length + ctors.length;
} else {
for(Method method : methods)
if(method.toString().indexOf(args[1]) != -1) {
System.out.println(p.matcher(method.toString()).replaceAll(""));
lines++;
}
for(Constructor ctor : ctors)
if(ctor.toString().indexOf(args[1]) != -1) {
System.out.println(p.matcher(ctor.toString()).replaceAll(""));
lines++;
}
}
} catch(ClassNotFoundException e) {
System.out.println("No such class: " + e);
}
}
}
10.Desgign patternul proxy
package laborator10;
interface Interface {
void doSomething();
void somethingElse(String arg);
}
class RealObject implements Interface {
public void doSomething() { System.out.println("doSomething"); }
public void somethingElse(String arg) {
System.out.println("somethingElse " + arg);
}
}
class SimpleProxy implements Interface {
//compozitia cu RealObject se face la nivelul interfetei
private Interface proxied;
//constructorul va initializa membrul proxied cu
//orice obiect care implementeaza interfata Interface
public SimpleProxy(Interface proxied) {
this.proxied = proxied;
}
public void doSomething() {
System.out.println("SimpleProxy doSomething");
proxied.doSomething();
}
public void somethingElse(String arg) {
System.out.println("SimpleProxy somethingElse " + arg);
proxied.somethingElse(arg);
}
}

class SimpleProxyDemo {
public static void consumer(Interface iface) {
iface.doSomething();
iface.somethingElse("bonobo");
}
public static void main(String[] args) {
consumer(new RealObject());
consumer(new SimpleProxy(new RealObject()));
}
}

11.DynamicProxy
package laborator10;
import java.lang.reflect.*;
class DynamicProxyHandler implements InvocationHandler {
private Object proxied; //compozitia se face la nivelul general Object
public DynamicProxyHandler(Object proxied) {
this.proxied = proxied;
}
//invocarea metodei din obiectul proxy se face cu ajutorul claselor Reflection
public Object invoke(Object proxy, Method method, Object[] args) throws
Throwable {
System.out.println("**** proxy: " + proxy.getClass() +
", method: " + method + ", args: " + args);
if(args != null)
for(Object arg : args)
System.out.println(" " + arg);

//se invoca metoda trimisa ca si argument


//din obiectul proxied cu argumentele date
return method.invoke(proxied, args);
}
}
class SimpleDynamicProxy {
public static void consumer(Interface iface) {
iface.doSomething();
iface.somethingElse("bonobo");
}
public static void main(String[] args) {
RealObject real = new RealObject();
consumer(real);
//Insert a proxy and call again:
Interface proxy = (Interface)Proxy.newProxyInstance(
Interface.class.getClassLoader(),
new Class[]{ Interface.class },
new DynamicProxyHandler(real));
consumer(proxy);
}
}

You might also like