Liste
Partendo da una struttura dati che deve realizzare una lista doppiamente linkata (con le classi per la lista e per i nodi che puntano ad oggetti qualunque), e con la lista che conta gli elementi contenuti:
si veda il codice allegato
Si scriva il codice del metodo che toglie nodi dalla lista, con una interfaccia di invocazione:
public void togli (int intero) throws ListException
Il metodo togli() deve portare ad una eliminazione di un insieme di nodi della lista, considerando intero come il numero di nodi passati i quali se ne deve eliminare uno. Il parametro intero rappresenta quindi la lunghezza della sequenza di nodi della lista dopo la quale scartare un elemento, per passare poi alla successiva sequenza, ecc.
Ad esempio, se intero è uguale a 1, si deve partire mantenendo l'eventuale primo nodo, eliminare il secondo, mantenere il terzo, e così via fino alla fine della lista. Se intero è uguale a 2, si deve partire mantenendo inalterati gli eventuali primi due nodi, eliminare il terzo, mantenere i successivi due, e così via fino alla fine della lista.
L'eccezione ListException deve essere lanciata nel caso in cui la lista non consenta la distruzione di nessun elemento.
public void togli (int intero)
throws ListException {
if(isEmpty() || (size <=
intero)) // non possiamo distruggere elementi !!!
throw new ListException("lista con troppo pochi elementi");
// almeno un elemento in
lista da togliere
DoubleListNode next, node = first; int i;
// finche' ci sono elementi
nella lista
while ( node.
getNext () != null)
{
i = 1;
while ((i <= intero) && node. getNext()!= null)
{node = node.getNext(); i++;}if (i > intero)
{next = node.getNext(); node.getPrev().setNext(next);
if (next !=null) { next.setPrev(node.getPrev()); node = next; }
// si va avanti solo se il nodo esiste
size--;}
}
}
Si noti l'uso delle eccezioni per fare una verifica delle condizioni operative.
Filtri
Si progetti un filtro che deve essere invocato con almeno due argomenti. Il primo argomento deve essere una stringa, tutti gli altri caratteri singoli. Non ci sono limiti superiori al numero degli argomenti. Si controlli che l'invocazione avvenga con il numero ed il formato corretto per gli argomenti.
Il filtro deve prendere l'ingresso da System.in e porre la propria uscita su System.out. Deve operare sul file di ingresso sostituendo ad ogni occorrenza dei caratteri uguali ai singoli caratteri argomento (tutti gli argomenti diversi dal primo) la stringa passata come primo argomento. Tutti gli altri caratteri del file di ingresso vengono lasciati inalterati e portati direttamente in uscita. Si noti che il filtro opera fino alla fine del file di ingresso, che può essere costituito da un numero qualunque di linee.
Ad esempio, il filtro, invocato come:
filtro pippo p a 3 I %
con input fornito da console pari a:
Esame per FINDAMENTI\n 313\n123456\n
Produce in uscita:
Espippome pippoer FpippoNDAMENTpippo\n pippo1pippo\n12pippo456\n"
package filtro;
import java.io.*;
public class Filtro {
public static void main(String[] args) {
char ch;int totale=0; char ch;
if (args.length < 2) {
System.out.println("Problemi di argomenti\n Sono " + args.length + " e devono essere piu' di 2"); System.exit(1); }
for (int i=1; i < args.length; i++)
if (args[i].length() != 1) {
System.out.println("Gli argomenti dal secondo un solo carattere" + "\n e non " + args[1].length()); System.exit(2);
}
filtra (args); System.exit(0);
}
public static void filtra(String[] args) {
InputStreamReader in = new InputStreamReader(System.in);
OutputStreamWriter out = new OutputStreamWriter(System.out);
int x;try {
while ((x = in.read()) >= 0) {
char ch = (char) x;
if (ch == '\n') {out.flush();}
// notate che si esamina un carattere alla volta
// e non si leggono linee o l'intero fileboolean trovato = false;
for (int i=1; i < args.length; i++)
if (ch == args[i].charAt(0)) {out.write(args[0]); trovato = true; break;}// si veda cosa succede con due argomenti uguali ???
// come si puo' migliorare il tutto ??if (!trovato) out.write(ch);
}
}
catch (IOException e) {
System.out.println("Errore. Problema nella scrittura ");
System.exit(3);
}
try { out.close();}
catch
(IOException e) {
System.out.println("Errore. Problema in chiusura");
System.exit(4);
}
}
}
Componenti grafici
Dato il seguente codice (disponibile anche attraverso questo collegamento):
public class Esame23luglio {
public static void main(String args[]) {
JButton input1 = new JButton("Ingresso
1");
JButton input2 = new JButton("Ingresso 2");
JLabel ilab1 = new JLabel("true");
JLabel ilab2 = new JLabel("true");
JLabel xor = new JLabel("XOR false");
JLabel and = new JLabel("AND true");
JPanel panel = new JPanel();
JFrame frame= new JFrame("Componente a Ingressi e Uscite");
frame.setBounds(200, 200, 150, 250);
frame.setResizable(false);
Container c = frame.getContentPanel();
c.add(panel);
...
frame.show();
}
}
Si progetti l'applicazione grafica che deve simulare un componente a molti ingressi, in particolare a due ingressi, e a molte uscite, in particolare a due uscite.
Ogni ingresso o uscita prevede due valori di ingresso, vero e falso. Ogni ingresso viene rappresentato da un bottone, che ha il compito di permettere la variazione dell'ingresso corrispondente, e da una label che si occupa di visualizzare lo stato corrente del bottone. Ogni uscita viene rappresentata da una label per visualizzare il valore di uscita del componente.
Ogni bottone deve essere inizializzato a partire da stato true e ogni pressione cambia l'ingresso, segnalandolo nel campo label corrispondente. Quindi, la prima pressione di un bottone deve segnalare nel testo corrispondente al bottone lo stato false, la successiva lo stato true, ecc. Ogni pressione di un bottone deve inoltre produrre l'eventuale aggiornamento delle due uscite.
Per le due uscite, si prevedono:
La soluzione prevede di avere il frame come unico listener per tutti gli eventi.
package esame23luglio;
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
public class Esame23luglio {
public static void main(String
args[]) {
JButton input1 = new JButton("Ingresso 1");
JButton input2 = new JButton("Ingresso 2");
JLabel ilab1 = new JLabel("true");
JLabel ilab2 = new JLabel("true");
JLabel xor = new JLabel("XOR false");
JLabel and = new JLabel("AND true");
JPanel panel =
new JPanel();
EsameFrame
frame= new EsameFrame("Componente
a Ingressi e Uscite",
input1, input2, ilab1, ilab2, xor, and);
frame.setBounds(200, 200, 150, 250);
frame.setResizable(false);Container c = frame.getContentPane();
c.add(panel);
panel.add(input1); panel.add(ilab1);
panel.add(input2); panel.add(ilab2);
panel.add(xor); panel.add(and);
input1.addActionListener
(frame);
input2.addActionListener
(frame);
frame.addWindowListener(new
Terminator ());
frame.show();
}
}
class EsameFrame extends JFrame
implements ActionListener {
private JLabel i1, i2,
AND, XOR;
private JButton b1, b2;
public EsameFrame (String
s, JButton b1, JButton b2,
JLabel i1,
JLabel i2, JLabel xor, JLabel and) {
super(s);
i1= b1; i2 = b2;
this.b1 = b1; this. b2
= b2;
XOR
= xor; AND = and;
}
public void actionPerformed(ActionEvent
e){
if (e.getSource()
== b1)
{ System.out.println
(" Ingresso 1 e " + i1.getText() + "\n");
if (i1.getText() == "true") i1.setText ("false");
else i1.setText("true");
}
if (e.getSource()
== b2)
{ System.out.println
(" Ingresso 2 e " + i2.getText() + "\n");
if (i2.getText() == "true") i2.setText ("false");
else i2.setText("true");
}
System.out.println (" Ingressi attuali " + i1.getText() + " " + i2.getText() + "\n");
if (i1.getText()
!= i2.getText())
XOR.setText("XOR vero \n");
else XOR.setText("XOR
falso \n");
if (i1.getText()==
"true" && i2.getText()==
"true")
AND.setText("AND
vero \n");
else AND.setText("AND
falso \n");
}
}
//----------------------------
class Terminator implements WindowListener {
public
void windowClosed(WindowEvent e){}
public void windowClosing(WindowEvent
e){ System.exit(0); }
public void windowOpened(WindowEvent
e){}
public void windowIconified(WindowEvent
e){}
public void windowDeiconified(WindowEvent
e){}
public void windowActivated(WindowEvent
e){}
public void windowDeactivated(WindowEvent
e){}
}
Non essendo richiesto un facoltativo, si consideri la possibilità di generalizzare il caso a molti ingressi e più funzioni di uscita.
Si veda la implementazione seguente che prevede
una invocazione del programma con un valore intero, che rappresenta il numero
di elementi da considerare.
Si noti la importanza di un linguaggio che consenta di istanziare un array decidendo
la dimensione al momento della esecuzione e non in fase di dichiarazione.
Di tutti gli ingressi si fa il solo AND: si consideri il caso di XOR. Ci sarebbero problemi?
package esamelugliofacoltativo;
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
public class Esame2 {
public static void main(String args[]) {
int i, n = 0;
JButton butts [];
JLabel txts [];
JLabel ANDlogico;
JLabel ANDlabel;
if (args.length != 1) {
System.out.println("Necessario
un argomento\n sono invece " + args.length);
System.exit(1);
}
try {
n = Integer.parseInt
(args[0]);
}
catch (NumberFormatException e)
{System.out.println ("Non
valore giusto: non intero");
System. exit (1);}
butts = new JButton [n];
txts = new JLabel [n];
for (i=0; i < n; i++)
{ butts [i] = new JButton("Ingresso " + i);
txts[i] = new JLabel("true");
}
JPanel panel = new JPanel();
EsameFrame frame= new EsameFrame("Frame
per Ingressi multipli ",
butts, txts, ANDlogico);
frame.setBounds(200, 100, 208, 400);
frame.setResizable(false);
Container c = frame.getContentPane();
c.add(panel);
for (i=0; i < n; i++)
{ panel.add(butts [i]);
panel.add(txts[i]);
butts[i].addActionListener
(frame);
}
ANDlabel= new JLabel ("AND
logico di " + n + "ingressi ");
ANDlogico= new JLabel ("AND true ");
panel.add(ANDlabel);
panel.add(ANDlogico);
frame.addWindowListener(new Terminator ());
frame.show();
}
}
class EsameFrame extends JFrame implements
ActionListener {
private JLabel txts[];
private JButton butts[];
private JLabel ANDlogico;
int n;
public EsameFrame (String t, JButton
bs[], JLabel ts [], JLabel ANDl)
{
super(t);
n = bs.length;
butts = new JButton [n];
txts = new JLabel [n];
ANDlogico = ANDl;
for ( int i = 0; i < n; i++)
{this. txts [i] = ts [i];
this. butts [i] = bs [i];
}
}
public void actionPerformed(ActionEvent e){
for (int i = 0 ; i < n; i++)
if (e.getSource() == butts[i])
{ System.out.println ("
Ingresso " + i);
if (txts[i].setText()
== "false") txts[i].setText ("true"); else txts[i].setText("false");
}
for (int i = 0; i < n; i++)
System.out.println (" Ingresso
" + i + " vale " + txts[i].setText());
ANDlogico. setText(" AND true
");
for (int i = 0; i < n; i++)
if (txts[i].getText () == "false") {
ANDlogico. setText(" AND falso "); break;}
}
}
//----------------------------
class Terminator implements WindowListener
{
public void windowClosed(WindowEvent
e){}
public void windowClosing(WindowEvent
e){ System.exit(0); }
public void windowOpened(WindowEvent
e){}
public void windowIconified(WindowEvent
e){}
public void windowDeiconified(WindowEvent
e){}
public void windowActivated(WindowEvent
e){}
public void windowDeactivated(WindowEvent
e){}
}