2015-02-11 24 views
6

JavaFX'te neden hiçbir ObservableQueue yok? Java 9 belgelerine baktığımızda (sadece 8'den herhangi bir değişiklik olup olmadığını görmek için), FXCollections için, Gözlemlenebilir kümeler, listeler ve haritalar oluşturmak için statik yardımcı yöntemler görüyoruz. Gözlemlenebilir yüzer ve tamsayı dizileri oluşturmak için bazı yöntemler vardır. Ancak, Gözlemlenebilir bir Sorgu oluşturmanın yolu yoktur. Java'daki Kuyruk arabirimi, ArrayDeque, DelayQueue, ConcurrentLinkedQueue, PriorityQueue, vb. Dahil olmak üzere pek çok ilginç uygulamaya sahiptir. JavaFX'te ObservableQueues oluşturmak için neden destek bulunmadığının arkasındaki mantık nedir.JavaFX'de neden hiçbir ObservableQueues yok?

cevap

6

@TomasMikula adlı kullanıcının yorumları @ eckig'in (şimdi silindi) cevabı, muhtemelen bir ObservableQueue için yeterli talep yok. Eğer sağlam bir kullanım durumunuz varsa, submitting a feature request'u düşünmelisiniz. Bu arada

, bu oluşturmak için çok zor değil bir Queue uygulanması ve ObservableListBase sınıflara ve bir Queue uygulanmasını sararak "gözlemlenebilirliği" ekleyerek ObservableQueue kirli hızlı ve-. Alt sınıflandırma ObservableListBase "hızlı" kısmıdır, ancak "kirli" kısım da List yöntemlerinin yanı sıra yöntemlerini gösterir; Bir rasgele Queue bir get(int index) sahip olmadığı için bunu uygulamak için tek yolu (görebildiğim), index'a kadar yineleme yapmaktır. List ile ilgili olarak ObservableQueue boyunca yinelemek için get kullanan her şey, O(n^2) zamanında çalışır. ki ihtar ile, şu oldukça iyi çalışması gerekir: Kuyruğa değişiklikler haberdar olmak için bununla ListChangeListener s kayıt olabilirsiniz

import java.util.LinkedList; 
import java.util.Queue; 

import javafx.collections.ObservableListBase; 


public class ObservableQueue<E> extends ObservableListBase<E> implements Queue<E> { 

    private final Queue<E> queue ; 


    /** 
    * Creates an ObservableQueue backed by the supplied Queue. 
    * Note that manipulations of the underlying queue will not result 
    * in notification to listeners. 
    * 
    * @param queue 
    */ 
    public ObservableQueue(Queue<E> queue) { 
     this.queue = queue ; 
    } 

    /** 
    * Creates an ObservableQueue backed by a LinkedList. 
    */ 
    public ObservableQueue() { 
     this(new LinkedList<>()); 
    } 

    @Override 
    public boolean offer(E e) { 
     beginChange(); 
     boolean result = queue.offer(e); 
     if (result) { 
      nextAdd(queue.size()-1, queue.size()); 
     } 
     endChange(); 
     return result ; 
    } 

    @Override 
    public boolean add(E e) { 
     beginChange() ; 
     try { 
      queue.add(e); 
      nextAdd(queue.size()-1, queue.size()); 
      return true ; 
     } finally { 
      endChange(); 
     } 
    } 


    @Override 
    public E remove() { 
     beginChange(); 
     try { 
      E e = queue.remove(); 
      nextRemove(0, e); 
      return e; 
     } finally { 
      endChange(); 
     } 
    } 

    @Override 
    public E poll() { 
     beginChange(); 
     E e = queue.poll(); 
     if (e != null) { 
      nextRemove(0, e); 
     } 
     endChange(); 
     return e ; 
    } 

    @Override 
    public E element() { 
     return queue.element(); 
    } 

    @Override 
    public E peek() { 
     return queue.peek(); 
    } 

    @Override 
    public E get(int index) { 
     Iterator<E> iterator = queue.iterator(); 
     for (int i = 0; i < index; i++) iterator.next(); 
     return iterator.next(); 
    } 

    @Override 
    public int size() { 
     return queue.size(); 
    } 

} 

. (Ekstraları desteklemek ve bildirimleri güncellemek istiyorsanız, biraz daha fazla çalışma yapmanız gerekeceğini unutmayın).

import javafx.collections.ListChangeListener.Change; 

public class ObservableQueueTest { 
    public static void main(String[] args) { 
     ObservableQueue<String> oq = new ObservableQueue<>(); 
     oq.addListener((Change<? extends String> change) -> { 
      while (change.next()) { 
       if (change.wasAdded()) { 
        System.out.println("Added: "+change.getAddedSubList()); 
       } 
       if (change.wasRemoved()) { 
        System.out.println("Removed: "+change.getRemoved()); 
       } 
       if (change.wasUpdated()) { 
        System.out.println("Updated: "+oq.subList(change.getFrom(), change.getTo())); 
       } 
       if (change.wasReplaced()) { 
        System.out.println("Replaced"); 
       } 
      } 
     }); 

     oq.offer("One"); 
     oq.offer("Two"); 
     oq.offer("Three"); 

     System.out.println("Peek: "+oq.peek()); 
     System.out.println("Remove..."); 
     System.out.println(oq.remove()); 

     System.out.println("Element:"); 
     System.out.println(oq.element()); 

     System.out.println("get(1): "+oq.get(1)); 

     System.out.println("Poll: "); 
     System.out.println(oq.poll()); 

     System.out.println("Poll again:"); 
     System.out.println(oq.poll()); 

     System.out.println("Poll should return null:"); 
     System.out.println(oq.poll()); 

     System.out.println("Element should throw exception:"); 
     System.out.println(oq.element()); 
    } 

} 
İlgili konular