Restituzione dei risultati del metodo nell'elenco dei lotti?

4

Il titolo è un po 'vago quindi proverò ad elaborare.

Ho una funzione

makeFoo(int bar) -> returns Foo or throws Exception.

Ho anche una versione batch di questo

makeFoos(int[] bars) -> returns Foo[]

che in pratica scorre su barre ed esegue makeFoo () su di esse.

Il problema è, se durante l'esecuzione di makeFoos (), makeFoo () genera un'eccezione, cosa devo fare? Non voglio uscire da makeFoos () perché voglio continuare a elaborare il resto delle barre. Ma anche, voglio mantenere l'eccezione che è stata lanciata.

La mia soluzione iniziale è, invece di restituire Foo [], restituisco Result < Foo > []. Dove Result è una classe wrapper:

class Result<T>:
    T data;
    Exception e;

C'è un modo migliore di avvicinarmi a questo?

Modifica: mi scuso se questo è considerato un post duplicato, ma ho postato una versione più generale di questa domanda qui: link

    
posta kennyg 07.07.2014 - 21:42
fonte

3 risposte

1

Restituisce una matrice di Facoltativa . A parte questo, potresti voler prendere in considerazione raccolte migliori rispetto agli array; sono piuttosto ingombranti, soprattutto perché non implementano Iterable o Collection.

MODIFICA: per rilevare il tipo di errore, il tuo Result<T> è un buon punto di partenza, ma non esporrò entrambi i campi in quel modo (presumo che tu l'abbia fatto solo per ottenere l'idea.) Result , o come è noto nei linguaggi funzionali, Either , è solo marginalmente diverso da Optional , quindi il tuo progetto finale dovrebbe avere approssimativamente la stessa API. In particolare, devi assolutamente implementare flatMap in modo da poter facilmente computare i calcoli sui risultati senza doverlo fare:

Result<T1> result1 = foo();
if (result1.isValue()) {
    T1 value1 = result1.getValue();
    Result<T2> result2 = bar(value1);
    if (result2.isValue()) {
        T2 value2 = result2.getValue();
        Result<T3> result3 = baz(value2);
        if (result3.isValue()) {
            ...
        } else {
            result3.getError();
        }
    } else {
        result2.getError();
    }
} else {
    result1.getError();
}

Normalmente direi che potresti voler parametrizzare il tipo di risultato anche sul tipo di errore, dal momento che potresti non voler sempre restituire un'eccezione, ma con l'inferenza di tipo praticamente inesistente di Java sarebbe solo rendere l'intero cosa ancora più ingombrante.

Potresti voler dare un'occhiata a questa domanda per un'alternativa all'implementazione dell'API dei risultati che non prevede la chiamata di getValue() se e solo se isValue() restituisce true.

    
risposta data 07.07.2014 - 23:22
fonte
0

Il semplice apporach è fallire solo quando una delle barre fallisce. Ma se vuoi elaborare l'intero elenco di barre, avrai bisogno di un oggetto più complesso che contenga array come:

  • SuccessfulFoos []
  • FailedBars []

FailedBars sarebbe un oggetto composito e incapsulerebbe anche le informazioni sull'errore. SuccessfulFoos sarebbe semplicemente un Foo poiché non si sono verificati errori.

    
risposta data 07.07.2014 - 21:52
fonte
0

In tutta onestà, mi piace di più la tua risposta. L'array di restituzione deve avere le stesse dimensioni dell'array di input, quindi è possibile determinare facilmente quali input hanno prodotto le uscite. Puoi anche scorrere l'array dei risultati e verificare se l'eccezione è nulla o no, e in caso contrario elaborare il risultato.

Un altro modo per farlo sarebbe quello di passare in un array che ha i parametri di input, il risultato di output e un'eccezione in un'area. In tal caso, è possibile restituire il numero di eccezioni (o non eccezioni o la prima eccezione) e si potrebbe ottenere un controllo rapido se tutto ha funzionato. Ad esempio:

class BatchedFoo
{
    int i;
    Foo data;
    Exception e;
}

makeFoos(BatchedFoo []) -> returns int
    
risposta data 09.07.2014 - 07:08
fonte

Leggi altre domande sui tag