Visualizzazione dei risultati da 1 a 6 su 6
  1. #1

    [Java] Dubbio su interfacce e classi astratte

    Mettiamo caso che io ho un interfaccia che si chiama "Item" con dentro le operazioni setName() e getName().

    Ora a questo punto, l'intefaccia l'unica nota positiva che ha è che poi posso implementare più tipi diversi di item assicurandomi che almeno quei due metodi avranno lo stesso prototipo. Quindi io potrei farmi un DiscreteItem ed un ContinuousItem che sono due classi che implementano quell'interfaccia e l'unica cosa che fa quell'interfaccia è vincolarmi a implementare quei metodi utilizzando sostanzialmente lo stesos numero e tipo di parametri e valori di ritorno. Ma non potrò mai dire che il metodo xyz richiede come parametro un interfaccia, oppure si?

    Cioè potro avere il metodo xyz(Item mioitem) ? ed in quel caso come funzionerebbe la cosa? potrei passargli un Discreteitem, che ha implementato tutti e due i metodi, e tutto funzionerebbe, o sto facendo confusione?

    Invece se parliamo di classe astratte, e non di interfacce, quindi mettiamo caso che abbiamo sempre Item, e solo che il metodo "setName()" lo implementiamo già ma il metodo "getName()" invece lo lasciamo da implementare. La cosa come cambia? in questo caso potrò avere un metodo che mi prende un item come parametro?

    Vi ringrazio in anticipo,
    Neptune.
    "Estremamente originale e fantasioso" By darkiko;
    "allora sfiga crepuscolare mi sa che e' meglio di atmosfera serale" By NyXo;
    "per favore, già è difficile con lui" By fcaldera;
    "se lo apri te e invece di "amore" ci metti "lavoro", l'effetto è lo stesso" By fred84

  2. #2
    In un progetto fatto per Algoritmi e Strutture Dati in C++ ad esempio stavo vedendo che ad esempio per la realizzazione delle Liste ho:

    Una superclasse Liste, con i vari metodi "Leggi, Scrivi, Primolista, ecc" tutti astratti e nella superclasse invece implementavo i vari algoritmi come il natural merge sort, la ricerca od altro. Poi la singola realizzazinone, ad esempio ListaConPuntatore ereditava dalla superclasse (nel codice ho qualcosa del tippo class ListaConPuntatore : public Lista{..}) ed implementava tutti i metodi astratti.

    A questo punto poi se mi creavo un oggetto di tipo Lista potevo utilizzare su i metodi della superclasse di ordinamento che avevo ereditato.

    In Java invece come funziona? Cioè se ho un interfaccia, come chiesto prima, posso ritrovarmi un un metodo che richiede un parametro che come tipo ha un interfaccia e magari richiamare metodi che saranno implementati poi da qualche altra classe?

    Ho un pò di confusione in testa, a quel punto quando poi mi creerò il mio DiscreteItem, potrò passarlo ad un algoritmo che richiedeva un parametro di tipo Item e basta? (contando che Item era solo un interfaccia).
    "Estremamente originale e fantasioso" By darkiko;
    "allora sfiga crepuscolare mi sa che e' meglio di atmosfera serale" By NyXo;
    "per favore, già è difficile con lui" By fcaldera;
    "se lo apri te e invece di "amore" ci metti "lavoro", l'effetto è lo stesso" By fred84

  3. #3
    Vedevo su questo esempio qui:
    http://nicchia.ingce.unibo.it/oop/we...t-classes.html

    Che praticamente anche in java è corretto ciò che dicevo, ovvero una classe astratta con n metodi astratti ed anche un solo metodo non astratto che richiama i metodi astratti. Poi sulle classi non astratte che la implementano potrò vedere quel metodo non astratto e richiamarlo.

    Ma quindi rimane un interrogativo, posso avere un metodo in una genrica classe che accetta un metodo di tipo astratto e a cui poi passerò una classe che implementa quel metodo?

    Chessò qualcosa del tipo:
    codice:
    class Miaclasse{
    ..
    public static chi_sei(item miooggetto)
    {
      System.Out.Println(miooggetto.getNome());
    }
    }
    ...
    main()
    {
     DiscreteItem di = new DiscreteItem();
     Miaclasse.chi_sei(di);
    }
    "Estremamente originale e fantasioso" By darkiko;
    "allora sfiga crepuscolare mi sa che e' meglio di atmosfera serale" By NyXo;
    "per favore, già è difficile con lui" By fcaldera;
    "se lo apri te e invece di "amore" ci metti "lavoro", l'effetto è lo stesso" By fred84

  4. #4
    Ho trovato questo esempio su internet che risponde "parzialmente alla mia domanda".
    Ovvero daccordo posso utilizzare i metodi astratti, poi però passo una classe implementa quell'interfaccia e tutto va a posto (credo che ugualmente valga sia per classi astratte che per interfacce).

    Ciò a cui non trovo risposta è posso avere un metodo che come parametro prenda proprio un interfaccia o una classe astratta, o no?

    Interfacce e polimorfismo
    Il polimorfismo ottenuto attraverso l'ereditarietà è uno strumento molto potente. Le interfacce ci permettono di sfruttare il polimorfismo anche senza ricorrere a gerarchie di ereditarietà. Vediamo un esempio:

    codice:
        public interface PricedItem { 
           public void setPrice(double price); 
           public double getPrice(); 
        }
    L'interfaccia PricedItem definisce il comportamento di un articolo con prezzo. Possiamo a questo punto implementare l'interfaccia in una classe applicativa Book nel modo seguente

    codice:
      public class Book implements PricedItem { 
            private String title; 
            private String author; 
            private double price; 
            ... 
            public void setPrice(double price) { 
                this.price = price; 
            } 
    
            public double getPrice() { 
                return price; 
            } 
        }
    Il codice client che necessita del prezzo di un libro può quindi essere scritto così:

    codice:
        double computeTotalPrice(Collection items) { 
            Iterator it = items.iterator(); 
            PricedItem item; 
            double total = 0; 
    
            while (it.hasNext()) { 
                item = (PricedItem)it.next(); 
                total += item.getPrice(); 
            } 
            return total; 
        }
    Il metodo precedente calcola il prezzo totale di una collezione di oggetti. Supponiamo ora di voler estendere l'applicazione per gestire non solo libri ma anche CD musicali. Introdurremo a questo proposito una nuova classe che implementa l'interfaccia PricedItem

    codice:
        public class CD implements PricedItem { 
            private String title; 
            private String singer; 
            private Collection songs; 
            private double price; 
            .... 
    
            public void setPrice(double price) { 
                this.price = price; 
            } 
    
            public double getPrice() { 
                return price; 
            } 
        }
    Il codice precedente per il calcolo del prezzo totale funziona senza modifiche anche se la collezione contiene oggetti di classe CD perchè tale codice fà riferimento all'interfaccia e non alla classe concreta.
    "Estremamente originale e fantasioso" By darkiko;
    "allora sfiga crepuscolare mi sa che e' meglio di atmosfera serale" By NyXo;
    "per favore, già è difficile con lui" By fcaldera;
    "se lo apri te e invece di "amore" ci metti "lavoro", l'effetto è lo stesso" By fred84

  5. #5
    Allora, il ragionamento è semplice: interfacce, classi astratte e classi concrete (le normali classi) considerali tipi.
    Ogni metodo restituisce una variabile di tipo Tipo e può avere dei parametri di tipo Tipo.
    Il vincolo che hai è che puoi creare oggetti solo da classi concrete, quindi se vuoi creare un oggetto di una classe astratta o un'interfaccia (classe con tutti i metodi astratti), devi definirne i metodi statici.
    Prendi ad esempio le collection Java: c'è un'interfaccia generale Collection che rappresenta un insieme di oggetti, con un metodo per aggiungerli, uno per rimuoverli, e un metodo iterator per scorrerne il contenuto. Poi ci sono diverse specializzazioni: c'è l'interfaccia List che rappresenta una lista di oggetti, oppure Map che è una lista di oggetti Entry che associano una chiave ad un valore, oppure ancora Set che rappresenta un insieme di elementi senza duplicati.

    Poi ci sono le classi concrete per esempio dell'interfaccia List, ArrayList che è una lista fatta da un array, quindi la migliore per la ricerca casuale (attraverso indice), oppure LinkedList che è piu' veloce nell'inserimento di molti oggetti ma piu' lenta nella ricerca casuale ecc...

    Se volessi effettuare un metodo per stampare a video il contenuto di una collection, con una libreria strutturata in questo modo, ti conviene comporre un metodo così?
    codice:
    public void printCollection (ArrayList<String> a) {
        int i = 0;
        for (String s : a) {
            System.out.println("Elemento " + i + ": " + s);
            i++;
        }
    }
    Se il programmatore volesse stampare i valori di una mappa? quel metodo non funzionerebbe e dovresti riscriverlo. Se invece viene scritto così:
    codice:
    public void printCollection (Collection<String> a) {
        int i = 0;
        for (String s : a) {
            System.out.println("Elemento " + i + ": " + s);
            i++;
        }
    }
    Tu puoi usare quel metodo con qualunque struttura che estende Collection, quindi con i Set, List e Map.
    lolide
    Java Programmer

    Informati

  6. #6
    Originariamente inviato da lolide
    Allora, il ragionamento è semplice: interfacce, classi astratte e classi concrete (le normali classi) considerali tipi.
    Ogni metodo restituisce una variabile di tipo Tipo e può avere dei parametri di tipo Tipo.
    Il vincolo che hai è che puoi creare oggetti solo da classi concrete, quindi se vuoi creare un oggetto di una classe astratta o un'interfaccia (classe con tutti i metodi astratti), devi definirne i metodi statici.
    Prendi ad esempio le collection Java: c'è un'interfaccia generale Collection che rappresenta un insieme di oggetti, con un metodo per aggiungerli, uno per rimuoverli, e un metodo iterator per scorrerne il contenuto. Poi ci sono diverse specializzazioni: c'è l'interfaccia List che rappresenta una lista di oggetti, oppure Map che è una lista di oggetti Entry che associano una chiave ad un valore, oppure ancora Set che rappresenta un insieme di elementi senza duplicati.

    Poi ci sono le classi concrete per esempio dell'interfaccia List, ArrayList che è una lista fatta da un array, quindi la migliore per la ricerca casuale (attraverso indice), oppure LinkedList che è piu' veloce nell'inserimento di molti oggetti ma piu' lenta nella ricerca casuale ecc...

    Se volessi effettuare un metodo per stampare a video il contenuto di una collection, con una libreria strutturata in questo modo, ti conviene comporre un metodo così?
    codice:
    public void printCollection (ArrayList<String> a) {
        int i = 0;
        for (String s : a) {
            System.out.println("Elemento " + i + ": " + s);
            i++;
        }
    }
    Se il programmatore volesse stampare i valori di una mappa? quel metodo non funzionerebbe e dovresti riscriverlo. Se invece viene scritto così:
    codice:
    public void printCollection (Collection<String> a) {
        int i = 0;
        for (String s : a) {
            System.out.println("Elemento " + i + ": " + s);
            i++;
        }
    }
    Tu puoi usare quel metodo con qualunque struttura che estende Collection, quindi con i Set, List e Map.

    Leggendo te ed anche un vecchio libro Java che avevo dall'infanzia forse ho captio come funziona, correggimi se sbaglio:

    Iniziando dalle interfacce, se ho un interfaccia Figura, e poi ho Cerchio e Quadrato che la implementano, con il solito metodo “paint” che ovviamente verrà implementato in maniera diversa da figura a figura, posso avere un metodo di una generica classe che accetti come parametro un oggetto di tipo figura per poi passargli in run-time un quadrato o un cerchio a seconda dell’occasione?

    Ovvero sarebbe corretto poter scrivere:
    public disegna(Figura f)
    {
    f.paint();
    }
    ed all’occorrenza passargli un Cerchio o un quadrato?
    Sarebbe anche possibile dichiarare un oggetto di tipo Figura istanziandola però come cerchio, ad esempio:
    Figura f = new Cerchio();
    Cioè benchè un interfaccia non può essere istanziata, è valido grossomodo il polimorfismo per inclusione? In modo da poter fare metodi che lavorano con figure generiche a cui poi al run-time passiamo una figura anziché un’altra?

    Riguardo le classi astratte, è vero quanto detto sopra? Cioè gli stessi esempi di sopra sarebbero validi se Figura fosse una classe astratta in cui l’operatore paint() non è implementato e Cerchio e Quadrato estendono Figura per poi in run-time poter chiamare il metodo disegna passandogli all’occorrenza un Cerchio o un Quadrato?
    Come è valida anche l’assegnazione ad f di tipo Figura (classe astratta) un oggetto di tipo Cerchio, esattamente come sopra ma con le classi astratte?
    Inoltre una classe se viene utilizzata la parola chiave abstract, anche se ha tutti i metodi implementati è comunque non istanziabile? Quindi per istanziarla bisognerà comunque fare una classe che in un certo modo “la estende” o no?
    Pur non potendola istanziare una classe astratta possiamo invocare eventuali metodi di classe a patto che siano ovviamente implementati?


    Detto in poche parole è vero che noi un interfaccia o una classe astratta non possiamo instanziarla, ma possiamo sfruttare il polimorfismo per inclusione ovvero, noi ci creiamo tranquillamente ad esempio il nostro algoritmo che ordina le liste lavorando sulla classe astratta liste (o sull'interfaccia liste). Poi però a quel metodo di ordinamento gli passerò una classe che implementa l'interfaccia liste (o estende la classe astratta liste) e quindi al run-time chiamera il giusto "leggi, scrivi, primolista". Ho capito bene il tutto?

    Soprattuto si chiama sempre polimorfismo per inclusione anche quando parliamo di interfacce e di classi astratte? perchè sul mio libro parla di "polimorfismo" ma non dice se ha un nome specifico
    "Estremamente originale e fantasioso" By darkiko;
    "allora sfiga crepuscolare mi sa che e' meglio di atmosfera serale" By NyXo;
    "per favore, già è difficile con lui" By fcaldera;
    "se lo apri te e invece di "amore" ci metti "lavoro", l'effetto è lo stesso" By fred84

Permessi di invio

  • Non puoi inserire discussioni
  • Non puoi inserire repliche
  • Non puoi inserire allegati
  • Non puoi modificare i tuoi messaggi
  •  
Powered by vBulletin® Version 4.2.1
Copyright © 2025 vBulletin Solutions, Inc. All rights reserved.