服务器:创建一个可以解决PuzzleUnsolved
的PuzzleSolvedpackage server;
import java.rmi.*;
import java.rmi.server.*;
import common.Puzzle;
import server.puzzleObject.PuzzleSolved;
import java.net.MalformedURLException;
class PuzzleSolver {
private static final String HOST = "localhost";
public static void main(String args[]) {
try {
String serverName = args[0];
Puzzle puzzle = new PuzzleSolved();
String rmiObServer = "rmi://" + HOST + "/" + serverName;
Naming.rebind(rmiObServer, puzzle);
System.out.println("Server ready");
}
catch(ArrayIndexOutOfBoundsException ex) {
System.out.println("Error! E' necessario specificare il nome del server");
}
catch(RemoteException r) {
System.out.println("Error while rebind object");
r.printStackTrace();
System.exit(1);
}
catch(MalformedURLException m) {
System.out.println("Error! Malformed url require");
}
}
}
客户端:创建一个PuzzleUnsolved然后需要看一个可解决的对象,然后使用PuzzleUnsolved运行求解
package client;
import java.rmi.*;
import java.io.Serializable;
import client.puzzleIO.*;
import common.Solvable;
import common.Puzzle;
import common.PuzzleUnsolved;
class PuzzleSolver {
private static final String HOST = "localhost";
public static void main(String args[]) {
PuzzleWriter writer = null;
PuzzleReader reader = null;
try {
String inputFile = args[0], outputFile = args[1], serverName = args[2];
writer = new PuzzleWriter();
reader = new PuzzleReader();
System.out.println("primo");
PuzzleUnsolved unsolved = new PuzzleUnsolved();
reader.read(unsolved, inputFile);
writer.write(unsolved, outputFile, false);
System.out.println("secondo");
Solvable ref = (Solvable) Naming.lookup("rmi://" + HOST + "/" + serverName);
ref.solve(unsolved);
writer.write(ref, outputFile, true);
System.out.println("fine");
}
catch(ArrayIndexOutOfBoundsException e) {
if(args.length == 0)
System.out.println("E' necessario specificare il file di input e di output");
if(args.length == 1)
System.out.println("File di output assente");
if(args.length == 2)
System.out.println("E' necessario specificare un nome per il server");
}
catch(ConnectException c) {
System.out.println("Problema di connessione con il server");
}
catch(Exception e) {
System.out.println("Si è verificato un problema nell'esecuzione");
e.printStackTrace();
}
}
}
拼图:抽象类
package common;
import java.rmi.*;
import java.rmi.server.*;
import java.util.ArrayList;
import java.io.Serializable;
import common.Solvable;
import common.PuzzleTile;
import common.PuzzleUnsolved;
public abstract class Puzzle extends UnicastRemoteObject implements Solvable{
private int rows = 0, columns = 0;
protected ArrayList<PuzzleTile> tiles = new ArrayList<PuzzleTile>();
public Puzzle() throws RemoteException {
}
public int rows(){
return rows;
}
public int columns(){
return columns;
}
public void setColumns(int columns) {
this.columns = columns;
}
public void setRows(int rows) {
this.rows = rows;
}
public void addTile(PuzzleTile t) {
tiles.add(t);
}
protected PuzzleTile tile(int row, int column) {
return tiles.get(row * columns + column);
}
public ArrayList<PuzzleTile> tiles() {
return tiles;
}
public abstract String toString();
public abstract void solve(PuzzleUnsolved puzzleToSolve) throws RemoteException;
}
PuzzleUnsolved:解决了难题
package common;
import java.rmi.*;
import java.io.Serializable;
import common.Puzzle;
import common.Solvable;
public class PuzzleUnsolved extends Puzzle implements Serializable {
public PuzzleUnsolved() throws RemoteException {
}
public String toString() {
StringBuilder aux = new StringBuilder();
for(int r = 0; r < this.rows(); ++r) {
for(int c = 0; c < this.columns(); ++c) {
aux.append(this.tile(r, c).character());
aux.append(" ");
}
}
aux.append(System.getProperty("line.separator"));
return aux.toString();
}
public void solve(PuzzleUnsolved puzzleToSolve) {
}
}
PuzzleSolved:解决的难题是解决了包含求解(...)方法的难题,成为一个解决的难题
package server.puzzleObject;
import java.rmi.*;
import java.rmi.server.*;
import java.util.ArrayList;
import java.io.Serializable;
import common.Puzzle;
import common.Solvable;
import common.PuzzleTile;
import common.PuzzleUnsolved;
public class PuzzleSolved extends Puzzle implements Solvable {
private ArrayList<PuzzleTile> tilesOrdered = new ArrayList<PuzzleTile>();
public PuzzleSolved() throws RemoteException {
}
public class PuzzleThread extends Thread {
public int row;
public PuzzleThread(int row) {
this.row = row;
}
public void run() {
for(int c = 0; c < columns(); ++c) {
boolean notFound = true;
for(int tile = 0; tile < tiles.size() && notFound; ++tile) {
if(tiles.get(tile).left().equals(tilesOrdered.get(row * columns() + c))) {
tilesOrdered.add(row * columns() + c, tiles.get(tile));
notFound = false;
}
}
}
}
}
public void solve(PuzzleUnsolved puzzle) throws RemoteException {
setColumns(puzzle.columns());
setRows(puzzle.rows());
tiles.addAll(puzzle.tiles());
tilesOrdered.addAll(puzzle.tiles());
solveFirstColumn();
solveRemaining();
}
public void solveFirstColumn() {
String top = "VUOTO";
for(int r = 0; r < rows(); ++r) {
boolean notFound = true;
for(int tile = 0; tile < tiles.size() && notFound; ++tile) {
if(tiles.get(tile).left().equals("VUOTO")) {
if(tiles.get(tile).top().equals(top)) {
tilesOrdered.set(r * columns(), tiles.get(tile));
top = tiles.get(tile).id();
notFound = false;
}
}
}
}
}
public void solveRemaining() {
for(int i = 0; i < rows(); ++i)
new PuzzleThread(i).start();
}
public PuzzleTile tile(int row, int column) {
return tilesOrdered.get(row * columns() + column);
}
public String toString() {
StringBuilder aux = new StringBuilder();
for(int r = 0; r < rows(); r++) {
aux.append(System.getProperty("line.separator"));
for(int c = 0; c < columns(); c++) {
aux.append(tile(r, c).character());
aux.append(" ");
}
}
aux.append(System.getProperty("line.separator") + System.getProperty("line.separator"));
aux.append(rows());
aux.append(" ");
aux.append(columns());
return aux.toString();
}
}
PuzzleTile:代表一个抽象拼图的瓷砖
package common;
import java.util.Arrays;
import java.io.Serializable;
public class PuzzleTile implements Serializable{
String id, letter, top, right, bottom, left;
public PuzzleTile(String id, String c, String t, String r, String b, String l) {
this.id = id;
letter = c;
top = t;
right = r;
bottom = b;
left = l;
}
public String id() {
return id;
}
public String top() {
return top;
}
public String right() {
return right;
}
public String bottom() {
return bottom;
}
public String left() {
return left;
}
public String character() {
return letter;
}
}
可解决 - 用于投射客户端远程PuzzleSolved的接口
package common;
import java.rmi.*;
import common.Puzzle;
import common.PuzzleUnsolved;
public interface Solvable extends Remote {
public void solve(PuzzleUnsolved puzzleToSolve) throws RemoteException;
}
当我尝试从客户端解决PuzzleUnsolved我得到这个堆栈错误:(
primo
secondo
java.lang.IllegalArgumentException: argument type mismatch
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at sun.rmi.server.UnicastServerRef.dispatch(UnicastServerRef.java:323)
at sun.rmi.transport.Transport$1.run(Transport.java:200)
at sun.rmi.transport.Transport$1.run(Transport.java:197)
at java.security.AccessController.doPrivileged(Native Method)
at sun.rmi.transport.Transport.serviceCall(Transport.java:196)
at sun.rmi.transport.tcp.TCPTransport.handleMessages(TCPTransport.java:568)
at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run0(TCPTransport.java:826)
at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.lambda$run$254(TCPTransport.java:683)
at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler$$Lambda$1/323034826.run(Unknown Source)
at java.security.AccessController.doPrivileged(Native Method)
at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run(TCPTransport.java:682)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
at sun.rmi.transport.StreamRemoteCall.exceptionReceivedFromServer(StreamRemoteCall.java:276)
at sun.rmi.transport.StreamRemoteCall.executeCall(StreamRemoteCall.java:253)
at sun.rmi.server.UnicastRef.invoke(UnicastRef.java:162)
at java.rmi.server.RemoteObjectInvocationHandler.invokeRemoteMethod(RemoteObjectInvocationHandler.java:194)
at java.rmi.server.RemoteObjectInvocationHandler.invoke(RemoteObjectInvocationHandler.java:148)
at com.sun.proxy.$Proxy0.solve(Unknown Source)
at client.PuzzleSolver.main(PuzzleSolver.java:33)
答案 0 :(得分:0)
远程接口与实际的远程方法不一致。您已经更改了远程方法的签名,而无需重建和重新部署整个系统。