Domanda

Invece di usare un selettore nel solito modo, dove per ogni canale pronto un messaggio può essere determinato e inviato, mi piacerebbe scegliere quale connessione è attualmente pronto e inviare un messaggio là.

Probabilmente questo può essere fatto lanciando tutti i canali in un selettore per la lettura e la marcatura li pronti per la lettura, se escono, quindi fare lo stesso per la scrittura, e poi scegliendo tra quelli che ho segnato pronto.

E 'una buona idea, c'è un modo migliore per fare questo, e quello che dovrebbe fare attenzione per? Ad esempio, il Rox Tutorial Uniti "Se si tenta di mescolare OP LEGGI e OP WRITE si prende subito nei guai. L'implementazione Sun Windows è stato visto a un punto morto, se si esegue questa operazione ". ci sono dei trucchi simili qui? Qual è il modo migliore per attuare:

boolean isReadyForRead(SocketChannel c);
boolean isReadyForWrite(SocketChannel c);
È stato utile?

Soluzione

Che ne dite di qualcosa di simile?

public static boolean isReadyForRead(SocketChannel socket) throws IOException {
    return isReady(socket, SelectionKey.OP_READ);
}

public static boolean isReadyForWrite(SocketChannel socket) throws IOException {
    return isReady(socket, SelectionKey.OP_WRITE);
}

public static boolean isReady(SocketChannel socket, int op) throws IOException {
    // Setup
    if (socket.isBlocking()) 
        throw new IllegalArgumentException("Socket must be in non-blocking mode");

    Selector selector = SelectorProvider.provider().openSelector();
    socket.register(selector, op);

    // Real work
    if (selector.selectNow() == 0)
        return false;
    // Just in case selector has other keys
    return selector.selectedKeys().contains(socket.keyFor(selector));
}

Questa chiamata è terribilmente inefficiente perché fa la messa a punto ogni volta. Se si dispone di una classe che racchiude, questo dovrebbe essere spostato fuori. Se si conosce selettore contiene una sola chiave, ultima riga può essere cambiato in "return true;".

sto solo facendo questo per divertimento. Non riesco a pensare ad uno scenario che questo sarà utile. Select () è stato progettato per dirvi lo stato di prese in modo efficiente e tutti dovrebbero usare che direttamente.

Altri suggerimenti

Si deve usare il tuo SelectionKey per verificare se un socket è pronto per la lettura o scrittura, quando il selettore si sveglia.

Ecco un molto utile tutorial sulla scrittura di un server NIO e http: //rox-xmlrpc.sourceforge.net/niotut/

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top