task4/solution07/src/org/apidesign/apifest08/currency/TableConvertor.java
author Jaroslav Tulach <jaroslav.tulach@apidesign.org>
Sat, 11 Oct 2008 23:38:46 +0200
changeset 61 58ec6da75f6f
parent 45 task3/solution07/src/org/apidesign/apifest08/currency/TableConvertor.java@251d0ed461fb
permissions -rw-r--r--
Copying structure for task4
japod@6
     1
package org.apidesign.apifest08.currency;
japod@6
     2
japod@6
     3
import java.util.Currency;
japod@6
     4
import java.util.HashMap;
japod@6
     5
import java.util.Map;
japod@6
     6
japod@6
     7
/**
japod@6
     8
 * A {@link Convertor} that works from a pre-set conversion table.
japod@6
     9
 * First use {@link #putIntoTable(org.apidesign.apifest08.currency.ConversionRate)} to set the conversion table.
japod@6
    10
 * Then invoke the {@link #convert(org.apidesign.apifest08.currency.Convertor.ConversionRequest)} method as many times as you wish.
japod@6
    11
 * @author jdvorak
japod@6
    12
 */
japod@6
    13
public class TableConvertor implements Convertor {
japod@6
    14
japod@6
    15
    private final Map<Currency, Map<Currency, ConversionRate>> conversionTable = new HashMap<Currency, Map<Currency, ConversionRate>>();
japod@6
    16
    
japod@6
    17
    public TableConvertor() {
japod@6
    18
    }
japod@6
    19
japod@6
    20
    /**
japod@6
    21
     * Puts a rate into the table.
japod@6
    22
     * @param rate
japod@6
    23
     */
japod@6
    24
    public void putIntoTable( final ConversionRate rate ) {
japod@6
    25
        final Currency srcCurrency = rate.getSrcUnitAmount().getCurrency();
japod@6
    26
        final Currency tgtCurrency = rate.getTgtUnitAmount().getCurrency();
japod@6
    27
        synchronized ( conversionTable ) {
japod@6
    28
            Map<Currency, ConversionRate> targetTable = conversionTable.get( srcCurrency );
japod@6
    29
            if ( targetTable == null ) {
japod@6
    30
                targetTable = new HashMap<Currency, ConversionRate>();
japod@6
    31
                conversionTable.put( srcCurrency, targetTable );
japod@6
    32
            }
japod@6
    33
            targetTable.put( tgtCurrency, rate );
japod@6
    34
        }
japod@6
    35
    }
japod@6
    36
    
japod@6
    37
    /**
japod@6
    38
     * Carries out the conversion.
japod@6
    39
     * If the table does not contain a conversion from the source currency to the target one,
japod@6
    40
     * a {@link ConversionResult} is returned that has null netAmount.
japod@6
    41
     * This implementation works with any {@link ConversionRequest}, it won't throw {@link IllegalRequestSubtypeException}.
japod@6
    42
     * @param req the conversion request
japod@6
    43
     * @return the conversion result
japod@6
    44
     */
japod@6
    45
    public ConversionResult convert( final ConversionRequest req ) {
japod@6
    46
        final Currency srcCurrency = req.getSrcAmount().getCurrency();
japod@6
    47
        final Currency tgtCurrency = req.getTgtCurrency();
japod@6
    48
        final ConversionRate rate = findConversionRate( srcCurrency, tgtCurrency );
japod@6
    49
        if ( rate != null ) {
japod@6
    50
            final MonetaryAmount tgtAmount = rate.convert( req.getSrcAmount() );
japod@6
    51
            return new ConversionResult( tgtAmount );
japod@6
    52
        } else {
japod@6
    53
            return new ConversionResult( null );    // did not find the pair of currencies in the table
japod@6
    54
        }
japod@6
    55
    }
japod@6
    56
japod@6
    57
    /**
japod@6
    58
     * Looks up the conversion between the given currencies in the table.
japod@6
    59
     * @param srcCurrency the source currency
japod@6
    60
     * @param tgtCurrency the target currency
japod@6
    61
     * @return the conversion rate; null means no conversion between the currencies was found in the table
japod@6
    62
     */
japod@6
    63
    protected ConversionRate findConversionRate( final Currency srcCurrency, final Currency tgtCurrency ) {
japod@6
    64
        synchronized ( conversionTable ) {
japod@6
    65
            final Map<Currency, ConversionRate> targetTable = conversionTable.get(srcCurrency);
japod@6
    66
            final ConversionRate rate = (targetTable != null) ? targetTable.get(tgtCurrency) : null;
japod@6
    67
            return rate;
japod@6
    68
        }
japod@6
    69
    }
japod@6
    70
japod@6
    71
}