Da WikiDsy.
//ROYV
import java.util.Hashtable;
// CLASSI di Figura3D ////////////////////////////////////////////////////////
class Cilindro extends Figura3D {
private double r, h;
public Cilindro(double r, double h) {
if (r <= 0 || h <= 0)
throw new Figura3DException(this.getClass().getName() + ": Parametro errato!");
else {
this.r = r;
this.h = h;
}
}
public void setParametri(double[] param) {
if (param == null || param.length < 2 || (param[0] <= 0 || param[1] <= 0))
throw new Figura3DException(this.getClass().getName() + ": Parametro errato!");
else {
this.r = param[0];
this.h = param[1];
}
}
public double[] getParametri() {
return new double[] {r, h};
}
public double getVolume() {
return Math.PI * r * r * h;
}
public double getSuperficie() {
return 2 * Math.PI * r * h;
}
public boolean equals(Object o) {
/* Confronto l' istanza attuale con l' istanza dell' oggeto.
Permettendo un confronto più specifico, nel caso il metodo venga utilizzato
da un eventuale sottoclasse.
*/
//return (o instanceof Cilindro) ? equals((Cilindro)o) : false;
return (this.getClass().isInstance(o))? equals((Cilindro)o) : false;
}
public boolean equals(Cilindro c) {
//test sui parametri dimensionali.
return this.r == c.r && this.h == c.h;
}
public String toString() {
return this.getClass().getName() + ": raggio = " + r + ", altezza = " + h;
}
}
class Sfera extends Cilindro {
public Sfera(double r) {
super(r, r);
}
public void setParametri(double[] param) {
if (param == null || param.length < 1)
throw new Figura3DException(this.getClass().getName() + ": Parametro errato!");
else
//crea una lista di due elementi costituiti dallo stesso valore.
super.setParametri(new double[] {param[0], param[0]});
}
public double[] getParametri() {
return new double[] {super.getParametri()[0]};
}
public double getVolume() {
//divisione tra valori double, 4/3 * volume del Cilindro.
return (4 * super.getVolume()) / 3;
}
public double getSuperficie() {
// 2 * (2PIhr)
return 2 * super.getSuperficie();
}
public String toString() {
return this.getClass().getName() + ": raggio = " + getParametri()[0];
}
}
class Parallelepipedo extends Figura3D {
private double a, b, h;
public Parallelepipedo(double a, double b, double h) {
if (a <= 0 || b <= 0 || h <= 0)
throw new Figura3DException(this.getClass().getName() + ": Parametro errato!");
else {
this.a = a;
this.b = b;
this.h = h;
}
}
public void setParametri(double[] param) {
if (param == null || param.length < 3 || (param[0] <= 0 || param[1] <= 0 || param[2] <= 0))
throw new Figura3DException(this.getClass().getName() + "Parametri non validi");
else {
this.a = param[0];
this.b = param[1];
this.h = param[2];
}
}
public double[] getParametri() {
return new double[] {a, b, h};
}
public double getVolume() {
return a * b * h;
}
public double getSuperficie() {
return 2 * (h * (a + b) + a * b);
}
public boolean equals(Object o) {
//stessa logica applicato sul metodo del Cilindro.
return (this.getClass().isInstance(o))? equals((Parallelepipedo)o) : false;
}
public boolean equals(Parallelepipedo p) {
return this.a == p.a && this.b == p.b && this.h == p.h;
}
public String toString() {
return this.getClass().getName() + ": latoA = " + a + ", latoB = " + b + ", altezza = " + h;
}
}
class Cubo extends Parallelepipedo {
public Cubo(double l) {
super(l, l, l);
}
public void setParametri(double[] param) {
if (param == null || param.length < 1)
throw new Figura3DException(this.getClass().getName() + ": Parametro errato!");
else
super.setParametri(new double[] {param[0], param[0], param[0]});
}
public double[] getParametri() {
return new double[] {super.getParametri()[0]} ;
}
public String toString() {
//lato -> raggio per confronto con i file di prova
return this.getClass().getName() + ": raggio = " + super.getParametri()[0];
}
}
class TroncoDiCono extends Figura3D {
private double rh, rs, h;
public TroncoDiCono(double rh, double rs, double h) {
if (rh <= 0 || rs < 0 || h <= 0)
throw new Figura3DException(this.getClass().getName() + ": Parametro errato!");
else {
this.rh = rh;
this.rs = rs;
this.h = h;
}
}
public void setParametri(double[] param) {
if (param == null || param.length < 3 || (param[0] <= 0 || param[1] < 0 || param[2] <= 0))
throw new Figura3DException(this.getClass().getName() + "Parametri non validi");
else {
this.rh = param[0];
this.rs = param[1];
this.h = param[2];
}
}
public double[] getParametri() {
return new double[] {rh, rs, h};
}
public double getVolume() {
return Math.PI / 3 * (rh * rs + rh * rh + rs * rs) * h;
}
public double getSuperficie() {
return Math.PI * (rh + rs) * Math.sqrt((rh - rs) * (rh - rs) + h * h);
}
public boolean equals(Object o) {
//return (o instanceof TroncoDiCono) ? equals( (TroncoDiCono) o) : false;
return (this.getClass().isInstance(o))? equals((TroncoDiCono)o) : false;
}
public boolean equals(TroncoDiCono t) {
return this.rh == t.rh && this.rs == t.rs && this.h == t.h;
}
public String toString() {
//return this.getClass().getName() + ": raggio grande = " + rh + ", raggio piccolo = " + rs + ", altezza = " + h;
return "Tronco di cono: raggio grande = " + rh + ", raggio piccolo = " + rs + ", altezza = " + h;
}
}
class Cono extends TroncoDiCono {
public Cono(double r, double h) {
super(r, 0, h);
}
public void setParametri(double[] param) {
if (param == null || param.length < 2)
throw new Figura3DException(this.getClass().getName() + ": Parametro errato!");
else
super.setParametri(new double[] {param[0], 0, param[1]});
}
public double[] getParametri() {
//utilizzo i parametri di TroncoDiCono Raggio Grande -> 0 e Altezza -> 2
double[] p = super.getParametri();
return new double[] {p[0], p[2]};
}
public String toString() {
double[] p = getParametri();
return this.getClass().getName() + ": raggio = " + p[0] + ", altezza = " + p[1];
}
}
class Figura3DException extends RuntimeException {
public Figura3DException(String msg) {
super(msg);
}
}
class TipoNonPrevistoException extends Exception {
public TipoNonPrevistoException(String msg) {
super(msg);
}
}
/////////////////////////////////////////////////////////////////////
class Architettura3D {
private Hashtable paramList;
private SequenzaFigure3D lista = null;
//identifica il tipo + generico di figura.
private static final String BASE_CLASS = "Figura3D";
public Architettura3D() {
lista = new SequenzaFigure3D();
inizializeParamList();
}
public void addFigura3D(Figura3D figura) {
lista.add(figura);
}
public Figura3D[] getFigure3D() {
return lista.toArray();
}
public double getVolume(String tipoFigura) throws TipoNonPrevistoException {
return lista.getSommaVolume(getBaseClass(tipoFigura));
}
public double getSuperficie(String tipoFigura) throws TipoNonPrevistoException {
return lista.getSommaSuperficie(getBaseClass(tipoFigura));
}
public double getVolumeMedio() {
return lista.getSommaVolume(BASE_CLASS) / lista.getSize();
}
public double getSuperficieMedia() {
return lista.getSommaSuperficie(BASE_CLASS) / lista.getSize();
}
public Figura3D trova(Figura3D fig) {
return lista.find(fig);
}
private String getBaseClass(String tipof) throws TipoNonPrevistoException {
String s;
if (tipof == null)
throw new TipoNonPrevistoException("Nessun parametro passato!");
else if ((s = (String)paramList.get(tipof)) == null)
throw new TipoNonPrevistoException("Il tipo " + tipof + " non è previsto!");
else
return s;
}
private void inizializeParamList() {
paramList = new Hashtable();
paramList.put("SC", "Cilindro");
paramList.put("PC", "Parallelepipedo");
paramList.put("TC", "TroncoDiCono");
paramList.put("TUTTE", BASE_CLASS);
}
}
// LISTA CONCATENATA
class SequenzaFigure3D {
//puntatore al primo nodo inizio della lista.
private NodoFigura inizio;
//puntatore all' ultimo nodo inizio della lista.
private NodoFigura fine;
//contatore degli elementi della lista.
private int nelem;
public SequenzaFigure3D() {
inizio = null;
fine = null;
nelem = 0;
}
private static class NodoFigura {
Figura3D figura;
NodoFigura pros;
}
public void add(Figura3D f) {
if (f == null)
throw new SequenzaFigure3DException("Parametro non valido!");
else {
NodoFigura n = new NodoFigura();
n.figura = f;
n.pros = null;
if (inizio == null)
inizio = n;
else
fine.pros = n;
fine = n;
nelem++;
}
}
public boolean remove(Figura3D f) {
if (f == null)
throw new SequenzaFigure3DException("Parametro non valido!");
else {
NodoFigura p = inizio, q = null;
//creazione del riferimento di sinistra e di destra della fig. da ricercare.
while (p != null && !f.equals(p.figura)) {
q = p;
p = p.pros;
}
//verifica della ricerca e gestione della posizione iniziale.
if (p != null && f.equals(p.figura)) {
if (q == null)
inizio = inizio.pros;
else
//eliminando l' unico riferimento l' oggetto verrà cancellato dal GC.
q.pros = p.pros;
nelem--;
return true;
}
return false;
}
}
public Figura3D find(Figura3D f) {
if (f == null)
throw new SequenzaFigure3DException("Parametro non valido!");
else {
NodoFigura nf = inizio;
//for(NodoFigura n = inizio.pros; n != null; n = n.pros)
//controllo delle figure dall' inizio della sequenza.
for (int i = 0; i < nelem; i++)
if (nf != null && f.equals(nf.figura))
return nf.figura;
else
nf = nf.pros;
return null;
}
}
public Figura3D[] toArray() {
NodoFigura nf = inizio;
Figura3D[] ls = new Figura3D[nelem];
for(int i = 0; i < nelem; i++) {
ls[i] = nf.figura;
nf = nf.pros;
}
return ls;
}
public boolean isEmpty() {
return inizio == null;
}
public int getSize() {
return nelem;
}
public double getSommaVolume(String tipoFigura) {
return sommaDati(inizio, tipoFigura, 'V');
}
public double getSommaSuperficie(String tipoFigura) {
return sommaDati(inizio, tipoFigura, 'S');
}
private double sommaDati(NodoFigura n, String filter, char c) {
/*
metodo basato sulla ricorsione.
caso base :
- nessun riferimento al nodo.
casi ricorsivi :
- Controllo istanze per tipo figura e in caso la figura corrente non
è della "categoria - filter" da utilizzare si rimanda al prossimo oggetto.
- Calcolo della proprietà "metodo da eseguire" e somma del risultato con
il calcolo applicato sulla prossima figura.
*/
double d = 0;
try {
if (n == null)
return 0;
//controllo dinamico sui tipi delle istanze.
else if (!Class.forName(filter).isInstance(n.figura))
return sommaDati(n.pros, filter, c);
else {
switch (c) {
case 'V':
d = n.figura.getVolume();
break;
case 'S':
d = n.figura.getSuperficie();
break;
default:
break;
}
return d + sommaDati(n.pros, filter, c);
}
}
//Gestione classe controllata.
catch (ClassNotFoundException e) {
throw new SequenzaFigure3DException("Tipo classe " + filter + " non trovata");
}
}
public String toString() {
return this.toString(" ");
}
public String toString(String sep) {
if (inizio == null)
return "";
else {
String s = inizio.figura.toString();
for(NodoFigura n = inizio.pros; n != null; n = n.pros)
s = s + sep + n.figura.toString();
return s;
}
}
}
class SequenzaFigure3DException extends RuntimeException {
public SequenzaFigure3DException(String msg) {
super(msg);
}
}