英文:
Send Object Over Java Socket
问题
我有一个名为Player的类
public JLabel imagen;
public String Nombre;
public Player(int x, int y, int width, int height, Icon icono, String name){
imagen = Player(x, y, width, height, icono);
Nombre = name;
}
public JLabel Player(int x, int y, int width, int height, Icon icono){
JLabel imagen = new JLabel(icono);
imagen.setLocation(x, y);
imagen.setSize(width, height);
return imagen;
}
(用于创建新玩家)
我还有一个客户端类:
public class Cliente implements Runnable {
String host;
int puerto;
Player mensaje;
public Cliente(int puerto, Player mensaje, String host){
this.puerto = puerto;
this.mensaje = mensaje;
this.host = host;
}
@Override
public void run() {
DataOutputStream out;
try {
Socket sc = new Socket(host, puerto);
out = new DataOutputStream(sc.getOutputStream());
ObjectOutputStream objectOutputStream = new ObjectOutputStream(out);
objectOutputStream.writeObject(mensaje);
sc.close();
} catch (IOException ex) {
System.out.println(ex);
}
}
}
并且我正在使用objectOutputStream,但它说
“java.io.NotSerializableException: objects.Player”
我想把我的玩家发送到服务器,但它显示了这个异常!
此外,如果您需要的话,这是服务器类:
public class Servidor extends Observable implements Runnable {
int puerto;
public Servidor(int puerto) {
this.puerto = puerto;
}
@Override
public void run() {
ServerSocket servidor = null;
Socket sc = null;
DataInputStream in;
try {
servidor = new ServerSocket(puerto);
System.out.println("服务器已启动");
while (true) {
sc = servidor.accept();
in = new DataInputStream(sc.getInputStream());
ObjectInputStream input = new ObjectInputStream(in);
Player players = null;
try {
players = (Player) input.readObject();
System.out.println(players.Nombre);
} catch (ClassNotFoundException ex) {
}
this.setChanged();
this.notifyObservers(players);
this.clearChanged();
sc.close();
}
} catch (IOException ex) {
}
}
}
如果您需要的话,这是发送请求到客户端类的代码行:
Cliente c = new Cliente(5000, new Player(x, y, width, height, icon, "玩家的名字"), "IP地址");
Thread t = new Thread(c);
t.start();
英文:
I have a class name player
public JLabel imagen;
public String Nombre;
public Player(int x, int y, int width, int height, Icon icono, String name){
imagen = Player(x, y, width, height, icono);
Nombre = name;
}
public JLabel Player(int x, int y, int width, int height, Icon icono){
JLabel imagen = new JLabel(icono);
imagen.setLocation(x, y);
imagen.setSize(width, height);
return imagen;
}
(It is for creating a new player)
I also have a client class:
public class Cliente implements Runnable {
String host;
int puerto;
Player mensaje;
public Cliente(int purto, Player mensaje, String host){
this.puerto = purto;
this.mensaje = mensaje;
this.host = host;
}
@Override
public void run() {
DataOutputStream out;
try {
Socket sc = new Socket(host, puerto);
out = new DataOutputStream(sc.getOutputStream());
ObjectOutputStream objectOutputStream = new ObjectOutputStream(out);
objectOutputStream.writeObject(mensaje);
sc.close();
} catch (IOException ex) {
System.out.println(ex);
}
}
}
And im using objectOutputStream but it says that it
"java.io.NotSerializableException: objects.Player"
And I want to send my player to the server but it says that exception!
Also if you need here is the server class
public class Servidor extends Observable implements Runnable {
int puerto;
public Servidor(int puerto) {
this.puerto = puerto;
}
@Override
public void run() {
ServerSocket servidor = null;
Socket sc = null;
DataInputStream in;
try {
servidor = new ServerSocket(puerto);
System.out.println("server started");
while (true) {
sc = servidor.accept();
in = new DataInputStream(sc.getInputStream());
ObjectInputStream input = new ObjectInputStream(in);
Player players = null;
try {
players = (Player) input.readObject();
System.out.println(players.Nombre);
} catch (ClassNotFoundException ex) {
}
this.setChanged();
this.notifyObservers(players);
this.clearChanged();
sc.close();
}
} catch (IOException ex) {
}
}
}
and also if you want here are the lines of code that send the request to the client class
Cliente c = new Cliente(5000, new Player(x, y, width, height, icon, "name of the player"), "the ip");
Thread t = new Thread(c);
t.start();
答案1
得分: 2
看起来你忘记把Player对象设置为可序列化(Serializable),所以代码抛出java.io.NotSerializableException
异常。
如果你需要在网络上传输某个对象,那么这个对象必须是可序列化的。
序列化是将对象的内存数据结构编码为一系列字节的过程。这个编码后的版本可以保存到磁盘,发送到网络连接,或以其他方式传递给接收者。(来自Wikipedia.org)
我已经更新了代码:
Player.java
import java.io.Serializable;
import javax.swing.Icon;
import javax.swing.JLabel;
public class Player implements Serializable {
private static final long serialVersionUID = 1L;
public JLabel imagen;
public String Nombre;
public Player(int x, int y, int width, int height, Icon icono, String name) {
imagen = createPlayer(x, y, width, height, icono);
Nombre = name;
}
public JLabel createPlayer(int x, int y, int width, int height, Icon icono) {
JLabel imagen = new JLabel(icono);
imagen.setLocation(x, y);
imagen.setSize(width, height);
return imagen;
}
}
Cliente.java
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.ObjectOutputStream;
import java.net.Socket;
public class Cliente implements Runnable {
String host;
int puerto;
Player mensaje;
public Cliente(int puerto, Player mensaje, String host) {
this.puerto = puerto;
this.mensaje = mensaje;
this.host = host;
}
public void run() {
try {
Socket sc = new Socket(host, puerto);
ObjectOutputStream objectOutputStream = new ObjectOutputStream(sc.getOutputStream());
objectOutputStream.writeObject(mensaje);
sc.close();
} catch (IOException ex) {
System.out.println(ex);
}
}
public static void main(String[] args) {
Cliente c = new Cliente(5000, new Player(1, 2, 3, 4, null, "Holis Studios"), "localhost");
Thread t = new Thread(c);
t.start();
}
}
Servidor.java
import java.io.DataInputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.Observable;
public class Servidor extends Observable implements Runnable {
int puerto;
public Servidor(int puerto) {
this.puerto = puerto;
}
public void run() {
ServerSocket servidor = null;
Socket sc = null;
DataInputStream in;
try {
servidor = new ServerSocket(puerto);
System.out.println("server started");
while (true) {
sc = servidor.accept();
in = new DataInputStream(sc.getInputStream());
ObjectInputStream input = new ObjectInputStream(in);
Player players = null;
try {
players = (Player) input.readObject();
System.out.println(players.Nombre);
} catch (ClassNotFoundException ex) {
}
this.setChanged();
this.notifyObservers(players);
this.clearChanged();
sc.close();
}
} catch (IOException ex) {
}
}
public static void main(String[] args) {
Servidor server = new Servidor(5000);
Thread t = new Thread(server);
t.start();
}
}
编译代码:
javac.exe -cp . Player.java
javac.exe -cp . Servidor.java
javac.exe -cp . Cliente.java
运行代码:
java.exe -cp . Servidor
在Servidor控制台上会输出:
server started
Holis Studios
英文:
Looks like you forgot to make the Player object Serializable, thus code is throwing java.io.NotSerializableException
If you need to send some object over network then the object need to be Serializable.
> Serialization is the process of taking the memory data structure of an
> object and encoding it into a serial (hence the term) sequence of
> bytes. This encoded version can then be saved to disk, sent across a
> network connection, or otherwise communicated to a recipient. (from
> Wikipedia.org)
I have updated the code
Player.java
import java.io.Serializable;
import javax.swing.Icon;
import javax.swing.JLabel;
public class Player implements Serializable {
/**
*
*/
private static final long serialVersionUID = 1L;
public JLabel imagen;
public String Nombre;
public Player(int x, int y, int width, int height, Icon icono, String name) {
imagen = Player(x, y, width, height, icono);
Nombre = name;
}
public JLabel Player(int x, int y, int width, int height, Icon icono) {
JLabel imagen = new JLabel(icono);
imagen.setLocation(x, y);
imagen.setSize(width, height);
return imagen;
}
}
Cliente.java
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.ObjectOutputStream;
import java.net.Socket;
public class Cliente implements Runnable {
String host;
int puerto;
Player mensaje;
public Cliente(int purto, Player mensaje, String host) {
this.puerto = purto;
this.mensaje = mensaje;
this.host = host;
}
// @Override
public void run() {
DataOutputStream out;
try {
Socket sc = new Socket(host, puerto);
out = new DataOutputStream(sc.getOutputStream());
ObjectOutputStream objectOutputStream = new ObjectOutputStream(out);
objectOutputStream.writeObject(mensaje);
sc.close();
} catch (IOException ex) {
System.out.println(ex);
}
}
public static void main(String[] args) {
Cliente c = new Cliente(5000, new Player(1, 2, 3, 4, null,
"Holis Studios"), "localhost");
Thread t = new Thread(c);
t.start();
}
}
Servidor.java
import java.io.DataInputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.Observable;
public class Servidor extends Observable implements Runnable {
int puerto;
public Servidor(int puerto) {
this.puerto = puerto;
}
// @Override
public void run() {
ServerSocket servidor = null;
Socket sc = null;
DataInputStream in;
try {
servidor = new ServerSocket(puerto);
System.out.println("server started");
while (true) {
sc = servidor.accept();
in = new DataInputStream(sc.getInputStream());
ObjectInputStream input = new ObjectInputStream(in);
Player players = null;
try {
players = (Player) input.readObject();
System.out.println(players.Nombre);
} catch (ClassNotFoundException ex) {
}
this.setChanged();
this.notifyObservers(players);
this.clearChanged();
sc.close();
}
} catch (IOException ex) {
}
}
public static void main(String[] args) {
Servidor server = new Servidor(5000);
Thread t = new Thread(server);
t.start();
}
}
Compiling the code:
javac.exe -cp . Player.java
javac.exe -cp . Servidor.java
javac.exe -cp . Cliente.java
Run:
java.exe -cp . Servidor
server started
java.exe -cp . Cliente
Output appearing on Servidor console:
server started
Holis Studios
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论