java - жалпы T түрінің данасын қалай жасауға болады

Мен серверді төмендегідей жазамын

public class Server {

    public void start() {

        try{
            this.serverSocket = new ServerSocket(this.port, this.backLog);
        } catch (IOException e) {
            LOGGER.error("Could not listen on port " + this.port, e);
            System.exit(-1);
        }

        while (!stopTheServer) {
            socket = null;
            try {
                socket = serverSocket.accept();
                handleNewConnectionRequest(socket);
            } catch (IOException e) {
                LOGGER.warn("Accept failed at: " + this.port, e);
                e.printStackTrace();
            }
        }

    }

    protected void handleNewConnectionRequest(Socket socket) {
        try {
            executorService.submit(new T(socket));
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

Бірақ handleNewConnectionRequest (...) әдісінде, T данасын жасай алмаймын, себебі ол шын мәнінде сынып емес. Сондай-ақ, мен қалағандай мұнда аталған әдісті пайдалана алмаймын socket данасын жіберіңіз, сонда сұрау өңдегіші OutputStream және InputStream ұяшығында ала алады.


Жоғарыда келтірілген сияқты жалпы серверді жасай алмаймын және әртүрлі протокол өңдегіштері бар, мысалы:

public class HttpRequestHandler extends RequestHandler {
    ...
}

public class FtpRequestHandler extends RequestHandler {
    ...
}

public class SmtpRequestHandler extends RequestHandler {
    ...
}

содан кейін оларды төмендегідей пайдаланыңыз

Server httpServer = new Server();
Server ftpServer = new Server();
Server smtpServer = new Server();
9

5 жауаптар

Сізге класс данасы қажет. Т типті T жеткіліксіз. Мынаны орындаңыз:

class Server  {
    Class clazz;
    public Server(Class clazz) {
        this.clazz = clazz;
    }

    private T newRequest() {
        return clazz.newInstance();
    }
}
9
қосылды

Әртүрлі өңдегіштерге сәйкес келетін Server > подкластерін жасауы мүмкін. Бір мысал:

public class HttpServer extends Server {

    protected HttpRequestHandler wrapSocket(Socket socket) {
        return new HttpRequestHandler(socket);
    }

}

Сондай-ақ серверді бейімдеу:

public abstract class Server {

    protected abstract T wrapSocket(Socket socket);

    protected void handleNewConnectionRequest(Socket socket) {
        try {
            executorService.submit(wrapSocket(socket));
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

}

Бір ой ғана ...

5
қосылды
+1. Немесе серверді RequestHandlerFactory пайдаланып, осы зауытты серверге қажет болған сайын RequestHandler жасауды сұраңыз.
қосылды автор JB Nizet, көзі
@JBNizet Эй, тіпті жақсы! Мен дерексіз сыныптар мен іске асырулар мен OO дизайнында шынымен жақсы дос болу үшін параметрлер параметрлерін таптым.
қосылды автор G_H, көзі

Жоқ. Бұл мағынасы жоқ. Бұл жағдайда мен генериктерден аулақ болар едім. Қарапайым ескі интерфейс немесе дерексіз класс жұмыс істейді. Дерексіз серверді дерексіз зауыттық әдіспен жасауға болады.

abstract class Server {
    abstract protected RequestHandler newRequest(Socket socket);
    ... same as before
}
1
қосылды
+1 Бұл, ең мағынасы бар және оңай оқуға жеңілдік береді. Мұнда Фабрика үлгісінен көп нәрсені алу үшін сенімді емеспін. Тілдік конструкциялар - бұл жолы.
қосылды автор Daniel B. Chapman, көзі

Оны тікелей Java-дегі генериктермен жасай алмайсыз. RequestHandler бағдарламасының нақты сынып нысанын getClass() арқылы алсаңыз, рефлексияны пайдалана аласыз. Сіз конструктордағы элементтің сыныбын сақтап көріп, келесідей көмекші әдіс жазуыңыз мүмкін:

Save the class object (in constructor for example):
this.clazz = requestHandler.getClass()

Then create new object of same class:
E instantiate(Class clazz)
{
    return clazz.newInstance();
}
0
қосылды
/* =================|Cassandra to Java Connection|===================== */
package demo_cassandra_connection;

import com.datastax.driver.core.Cluster;
import com.datastax.driver.core.Row;
import com.datastax.driver.core.Session;

public class java_to_cassandra_connection 
{
    public static void main(String[] args) 
    {
        com.datastax.driver.core.Session ses;
        Cluster cluster= 
        Cluster.builder().addContactPoints("54.191.46.102", 
       "54.149.32.12", "54.191.43.254")
        .withPort(9042).withCredentials("cassandra","cassandra").build();
        ses = cluster.connect();
        Session session = (Session) cluster.connect();
        String cqlStatement = "SELECT * FROM testapp.user";
        for (Row row : ((com.datastax.driver.core.Session) 
        session).execute(cqlStatement)) 
        {
            System.out.println(row.toString());
        }

    }
}
0
қосылды