近几天对FutureTask(Runnable runnable, V result)的用法百思不得其解。求一示例代码,要求用runnable在一个线程中生成一个随机数,然后通过result返回。注:FutureTask是java.util.concurrent包中的类,JDK1.5加入

解决方案 »

  1.   

    建议楼主看看多线程的东东,并不难.写一个线程,把 result 初始化进去, 线程启动往里存东西就行了.
    主程序要监控线程运行状态, 当线程执行完后, 再读 result.
      

  2.   

    34.public class FutureTask<V> implements Future<V>, Runnable {
    35.    /** Synchronization control for FutureTask */
    36.    private final Sync sync;
    37.
    38.    /**
    39.     * Creates a <tt>FutureTask</tt> that will upon running, execute the
    40.     * given <tt>Callable</tt>.
    41.     *
    42.     * @param  callable the callable task
    43.     * @throws NullPointerException if callable is null
    44.     */
    45.    public FutureTask(Callable<V> callable) {
    46.        if (callable == null)
    47.            throw new NullPointerException();
    48.        sync = new Sync(callable);
    49.    }
    50.
    51.    /**
    52.     * Creates a <tt>FutureTask</tt> that will upon running, execute the
    53.     * given <tt>Runnable</tt>, and arrange that <tt>get</tt> will return the
    54.     * given result on successful completion.
    55.     *
    56.     * @param  runnable the runnable task
    57.     * @param result the result to return on successful completion. If
    58.     * you don't need a particular result, consider using
    59.     * constructions of the form:
    60.     * <tt>Future<?> f = new FutureTask<Object>(runnable, null)</tt>
    61.     * @throws NullPointerException if runnable is null
    62.     */
    63.    public FutureTask(Runnable runnable, V result) {
    64.        sync = new Sync(Executors.callable(runnable, result));
    65.    }
    66.
    67.    public boolean isCancelled() {
    68.        return sync.innerIsCancelled();
    69.    }
    70.    
    71.    public boolean isDone() {
    72.        return sync.innerIsDone();
    73.    }
    74.
    75.    public boolean cancel(boolean mayInterruptIfRunning) {
    76.        return sync.innerCancel(mayInterruptIfRunning);
    77.    }
    78.    
    79.    public V get() throws InterruptedException, ExecutionException {
    80.        return sync.innerGet();
    81.    }
    82.
    83.    public V get(long timeout, TimeUnit unit)
    84.        throws InterruptedException, ExecutionException, TimeoutException {
    85.        return sync.innerGet(unit.toNanos(timeout));
    86.    }
    87.
    88.    /**
    89.     * Protected method invoked when this task transitions to state
    90.     * <tt>isDone</tt> (whether normally or via cancellation). The
    91.     * default implementation does nothing.  Subclasses may override
    92.     * this method to invoke completion callbacks or perform
    93.     * bookkeeping. Note that you can query status inside the
    94.     * implementation of this method to determine whether this task
    95.     * has been cancelled.
    96.     */
    97.    protected void done() { }
    98.
    99.    /**
    100.     * Sets the result of this Future to the given value unless
    101.     * this future has already been set or has been cancelled.
    102.     * @param v the value
    103.     */ 
    104.    protected void set(V v) {
    105.        sync.innerSet(v);
    106.    }
    107.
    108.    /**
    109.     * Causes this future to report an <tt>ExecutionException</tt>
    110.     * with the given throwable as its cause, unless this Future has
    111.     * already been set or has been cancelled.
    112.     * @param t the cause of failure.
    113.     */ 
    114.    protected void setException(Throwable t) {
    115.        sync.innerSetException(t);
    116.    }
    117.    
    118.    /**
    119.     * Sets this Future to the result of computation unless
    120.     * it has been cancelled.
    121.     */
    122.    public void run() {
    123.        sync.innerRun();
    124.    }
    125.
    126.    /**
    127.     * Executes the computation without setting its result, and then
    128.     * resets this Future to initial state, failing to do so if the
    129.     * computation encounters an exception or is cancelled.  This is
    130.     * designed for use with tasks that intrinsically execute more
    131.     * than once.
    132.     * @return true if successfully run and reset
    133.     */
    134.    protected boolean runAndReset() {
    135.        return sync.innerRunAndReset();
    136.    }
    137.
    138.    /**
    139.     * Synchronization control for FutureTask. Note that this must be
    140.     * a non-static inner class in order to invoke the protected
    141.     * <tt>done</tt> method. For clarity, all inner class support
    142.     * methods are same as outer, prefixed with "inner".
    143.     *
    144.     * Uses AQS sync state to represent run status
    145.     */
    146.    private final class Sync extends AbstractQueuedSynchronizer {
    147.        /** State value representing that task is running */
    148.        private static final int RUNNING   = 1;
    149.        /** State value representing that task ran */
    150.        private static final int RAN       = 2;
    151.        /** State value representing that task was cancelled */
    152.        private static final int CANCELLED = 4;
    153.
    154.        /** The underlying callable */
    155.        private final Callable<V> callable;
    156.        /** The result to return from get() */
    157.        private V result;
    158.        /** The exception to throw from get() */
    159.        private Throwable exception;
    160.
    161.        /** 
    162.         * The thread running task. When nulled after set/cancel, this
    163.         * indicates that the results are accessible.  Must be
    164.         * volatile, to ensure visibility upon completion.
    165.         */
    166.        private volatile Thread runner;
    167.
    168.        Sync(Callable<V> callable) {
    169.            this.callable = callable;
    170.        }
    171.
    172.        private boolean ranOrCancelled(int state) {
    173.            return (state & (RAN | CANCELLED)) != 0;
    174.        }
    175.
    176.        /**
    177.         * Implements AQS base acquire to succeed if ran or cancelled
    178.         */
    179.        protected int tryAcquireShared(int ignore) {
    180.            return innerIsDone()? 1 : -1;
    181.        }
    182.
    183.        /**
    184.         * Implements AQS base release to always signal after setting
    185.         * final done status by nulling runner thread.
    186.         */
    187.        protected boolean tryReleaseShared(int ignore) {
    188.            runner = null;
    189.            return true; 
    190.        }
    191.
    192.        boolean innerIsCancelled() {
    193.            return getState() == CANCELLED;
    194.        }
    195.        
    196.        boolean innerIsDone() {
    197.            return ranOrCancelled(getState()) && runner == null;
    198.        }
    199.
    200.        V innerGet() throws InterruptedException, ExecutionException {
    201.            acquireSharedInterruptibly(0);
    202.            if (getState() == CANCELLED)
    203.                throw new CancellationException();
    204.            if (exception != null)
    205.                throw new ExecutionException(exception);
    206.            return result;
    207.        }
    208.
    209.        V innerGet(long nanosTimeout) throws InterruptedException, ExecutionException, TimeoutException {
    210.            if (!tryAcquireSharedNanos(0, nanosTimeout))
    211.                throw new TimeoutException();                
    212.            if (getState() == CANCELLED)
    213.                throw new CancellationException();
    214.            if (exception != null)
    215.                throw new ExecutionException(exception);
    216.            return result;
    217.        }
    218.
    219.        void innerSet(V v) {
    220.     for (;;) {
    221. int s = getState();
    222. if (ranOrCancelled(s))
    223.     return;
    224. if (compareAndSetState(s, RAN))
    225.     break;
    226.     }
    227.            result = v;
    228.            releaseShared(0);
    229.            done();
    230.        }
    231.
    232.        void innerSetException(Throwable t) {
    233.     for (;;) {
    234. int s = getState();
    235. if (ranOrCancelled(s))
    236.     return;
    237. if (compareAndSetState(s, RAN))
    238.     break;
    239.     }
    240.            exception = t;
    241.            result = null;
    242.            releaseShared(0);
    243.            done();
    244.        }
    245.
    246.        boolean innerCancel(boolean mayInterruptIfRunning) {
    247.     for (;;) {
    248. int s = getState();
    249. if (ranOrCancelled(s))
    250.     return false;
    251. if (compareAndSetState(s, CANCELLED))
    252.     break;
    253.     }
    254.            if (mayInterruptIfRunning) {
    255.                Thread r = runner;
    256.                if (r != null)
    257.                    r.interrupt();
    258.            }
    259.            releaseShared(0);
    260.            done();
    261.            return true;
    262.        }
    263.
    264.        void innerRun() {
    265.            if (!compareAndSetState(0, RUNNING)) 
    266.                return;
    267.            try {
    268.                runner = Thread.currentThread();
    269.                innerSet(callable.call());
    270.            } catch(Throwable ex) {
    271.                innerSetException(ex);
    272.            } 
    273.        }
    274.
    275.        boolean innerRunAndReset() {
    276.            if (!compareAndSetState(0, RUNNING)) 
    277.                return false;
    278.            try {
    279.                runner = Thread.currentThread();
    280.                callable.call(); // don't set result
    281.                runner = null;
    282.                return compareAndSetState(RUNNING, 0);
    283.            } catch(Throwable ex) {
    284.                innerSetException(ex);
    285.                return false;
    286.            } 
    287.        }
    288.    }
    289.}
      

  3.   

    import java.util.concurrent.FutureTask;
    public class FutureCallableDemo {
    public static long fibonacci(long n) {
    if(n <=1) {
    return n;
    } else {
    return fibonacci(n-1) + fibonacci(n-2);
    }
    }
    /**
     * @param args
     */
    public static void main(String[] args) {
    class Result {
    private long result;
    }
    final Result r = new Result();
    FutureTask<Result> fib30 = new FutureTask<>(
    new Runnable() {
    @Override
    public void run() {
    r.result = fibonacci(30);
    }

    }
    , r);
    System.out.println("老闆,我要第30個費式數,待會來拿...");
    new Thread(fib30).start();
    System.out.println("忙別的事去...");
    try {
    Thread.sleep(5000);
    System.out.printf("第30個費式數:%d%n", fib30.get().result);
    } catch(Exception ex) {
    ex.printStackTrace();
    }
    }}