Java 反序列化序列化对象时发生ClassNotFound异常
我正在尝试序列化和反序列化一个对象。此对象可以包含对其他对象、ArrayList和HashMap的引用 当我尝试执行代码时,序列化可以正常工作,但反序列化不行。它会导致以下异常:Java 反序列化序列化对象时发生ClassNotFound异常,java,object,exception,serialization,classnotfoundexception,Java,Object,Exception,Serialization,Classnotfoundexception,我正在尝试序列化和反序列化一个对象。此对象可以包含对其他对象、ArrayList和HashMap的引用 当我尝试执行代码时,序列化可以正常工作,但反序列化不行。它会导致以下异常: Exception in thread "main" java.lang.ClassNotFoundException: experiment.Experiment$1 at java.net.URLClassLoader.findClass(URLClassLoader.java:381) at ja
Exception in thread "main" java.lang.ClassNotFoundException: experiment.Experiment$1
at java.net.URLClassLoader.findClass(URLClassLoader.java:381)
at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:331)
at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Class.java:348)
at javax.crypto.extObjectInputStream.resolveClass(SealedObject.java:490)
at java.io.ObjectInputStream.readNonProxyDesc(ObjectInputStream.java:1613)
at java.io.ObjectInputStream.readClassDesc(ObjectInputStream.java:1518)
at java.io.ObjectInputStream.readOrdinaryObject(ObjectInputStream.java:1774)
at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1351)
at java.io.ObjectInputStream.defaultReadFields(ObjectInputStream.java:2000)
at java.io.ObjectInputStream.readSerialData(ObjectInputStream.java:1924)
at java.io.ObjectInputStream.readOrdinaryObject(ObjectInputStream.java:1801)
at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1351)
at java.io.ObjectInputStream.readObject(ObjectInputStream.java:371)
at javax.crypto.SealedObject.getObject(SealedObject.java:302)
at experiment.Experiment.main(Experiment.java:52)
Java Result: 1
我的主要课程是实验,如下所示:
public class Experiment {
public static void main(String[] args) throws Exception {
File data = new File("C:\\Users\\Furze\\Desktop\\experiment.dat");
// I only execute the following to encrypt the file, which works fine:
Test test = new Test(new VariableMap<String, String>() {{
put("Name", "Furze");
}});
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.ENCRYPT_MODE, new SecretKeySpec(new byte[] {0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07}, "Blowfish"));
SealedObject sealedObject = new SealedObject(test, cipher);
CipherOutputStream outputStream = new CipherOutputStream(new BufferedOutputStream(new FileOutputStream(data.getPath())), cipher);
ObjectOutputStream objectOutput = new ObjectOutputStream(outputStream);
objectOutput.writeObject(sealedObject);
objectOutput.close();
// I then comment out the above code to test the file, which fails.
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.DECRYPT_MODE, new SecretKeySpec(new byte[] {0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07}, "Blowfish"));
CipherInputStream inputStream = new CipherInputStream(new BufferedInputStream(new FileInputStream(data.getPath())), cipher);
ObjectInputStream objectInput = new ObjectInputStream(inputStream);
SealedObject sealedObject = (SealedObject) objectInput.readObject();
Test test = (Test) sealedObject.getObject(cipher);
System.out.println(test.variables.get("Name"));
}
}
// The VariableMap class is something I added during debugging to test if HashMap simply isn't serializable. It didn't help. It does have to stay a HashMap (or VariableMap!) however, for my code to operate correctly.
class VariableMap<Name, Value> extends HashMap<String, String> implements java.io.Serializable {
public VariableMap() {
super();
}
}
public class Test implements java.io.Serializable {
VariableMap<String, String> variables = new VariableMap<>();
public Test() {}
public Test(VariableMap<String, String> variables) {
this.variables = variables;
}
}
有人能解释一下我的代码出了什么问题吗?我已经读过关于更改类路径的内容,但当我尝试更改时,没有任何区别。您缺少类顶部的包声明,它应该是:
package experiment;
public class Experiment implements Serializable {
public static void main(String[] args) throws Exception {
File data = new File("C:\\Users\\Furze\\Desktop\\experiment.dat");
// I only execute the following to encrypt the file, which works fine:
Test test = new Test(new VariableMap<String, String>() {{
put("Name", "Furze");
}});
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.ENCRYPT_MODE, new SecretKeySpec(new byte[] {0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07}, "Blowfish"));
SealedObject sealedObject = new SealedObject(test, cipher);
CipherOutputStream outputStream = new CipherOutputStream(new BufferedOutputStream(new FileOutputStream(data.getPath())), cipher);
ObjectOutputStream objectOutput = new ObjectOutputStream(outputStream);
objectOutput.writeObject(sealedObject);
objectOutput.close();
// I then comment out the above code to test the file, which fails.
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.DECRYPT_MODE, new SecretKeySpec(new byte[] {0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07}, "Blowfish"));
CipherInputStream inputStream = new CipherInputStream(new BufferedInputStream(new FileInputStream(data.getPath())), cipher);
ObjectInputStream objectInput = new ObjectInputStream(inputStream);
SealedObject sealedObject = (SealedObject) objectInput.readObject();
Test test = (Test) sealedObject.getObject(cipher);
System.out.println(test.variables.get("Name"));
}
}
包装实验;
公共类实验实现可序列化{
公共静态void main(字符串[]args)引发异常{
文件数据=新文件(“C:\\Users\\Furze\\Desktop\\Experience.dat”);
//我只执行以下操作来加密文件,效果很好:
测试=新测试(新变量映射(){{
放置(“名称”、“Furze”);
}});
Cipher Cipher=Cipher.getInstance(“河豚”);
cipher.init(cipher.ENCRYPT_模式,新的SecretKeySpec(新字节[]{0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07},“河豚”);
SealedObject SealedObject=新的SealedObject(测试,密码);
CipherOutputStream outputStream=新的CipherOutputStream(新的BufferedOutputStream(data.getPath()),cipher);
ObjectOutputStream objectOutput=新的ObjectOutputStream(outputStream);
objectOutput.writeObject(sealedObject);
objectOutput.close();
//然后我注释掉上面的代码来测试文件,但失败了。
Cipher Cipher=Cipher.getInstance(“河豚”);
cipher.init(cipher.DECRYPT_模式,新的SecretKeySpec(新字节[]{0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07},“河豚”);
CipherInputStream inputStream=new CipherInputStream(new BufferedInputStream(new FileInputStream(data.getPath())),cipher);
ObjectInputStream objectInput=新ObjectInputStream(inputStream);
SealedObject SealedObject=(SealedObject)objectInput.readObject();
Test=(Test)sealedObject.getObject(密码);
System.out.println(test.variables.get(“Name”);
}
}
您缺少类顶部的包声明,它应该是:
package experiment;
public class Experiment implements Serializable {
public static void main(String[] args) throws Exception {
File data = new File("C:\\Users\\Furze\\Desktop\\experiment.dat");
// I only execute the following to encrypt the file, which works fine:
Test test = new Test(new VariableMap<String, String>() {{
put("Name", "Furze");
}});
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.ENCRYPT_MODE, new SecretKeySpec(new byte[] {0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07}, "Blowfish"));
SealedObject sealedObject = new SealedObject(test, cipher);
CipherOutputStream outputStream = new CipherOutputStream(new BufferedOutputStream(new FileOutputStream(data.getPath())), cipher);
ObjectOutputStream objectOutput = new ObjectOutputStream(outputStream);
objectOutput.writeObject(sealedObject);
objectOutput.close();
// I then comment out the above code to test the file, which fails.
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.DECRYPT_MODE, new SecretKeySpec(new byte[] {0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07}, "Blowfish"));
CipherInputStream inputStream = new CipherInputStream(new BufferedInputStream(new FileInputStream(data.getPath())), cipher);
ObjectInputStream objectInput = new ObjectInputStream(inputStream);
SealedObject sealedObject = (SealedObject) objectInput.readObject();
Test test = (Test) sealedObject.getObject(cipher);
System.out.println(test.variables.get("Name"));
}
}
包装实验;
公共类实验实现可序列化{
公共静态void main(字符串[]args)引发异常{
文件数据=新文件(“C:\\Users\\Furze\\Desktop\\Experience.dat”);
//我只执行以下操作来加密文件,效果很好:
测试=新测试(新变量映射(){{
放置(“名称”、“Furze”);
}});
Cipher Cipher=Cipher.getInstance(“河豚”);
cipher.init(cipher.ENCRYPT_模式,新的SecretKeySpec(新字节[]{0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07},“河豚”);
SealedObject SealedObject=新的SealedObject(测试,密码);
CipherOutputStream outputStream=新的CipherOutputStream(新的BufferedOutputStream(data.getPath()),cipher);
ObjectOutputStream objectOutput=新的ObjectOutputStream(outputStream);
objectOutput.writeObject(sealedObject);
objectOutput.close();
//然后我注释掉上面的代码来测试文件,但失败了。
Cipher Cipher=Cipher.getInstance(“河豚”);
cipher.init(cipher.DECRYPT_模式,新的SecretKeySpec(新字节[]{0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07},“河豚”);
CipherInputStream inputStream=new CipherInputStream(new BufferedInputStream(new FileInputStream(data.getPath())),cipher);
ObjectInputStream objectInput=新ObjectInputStream(inputStream);
SealedObject SealedObject=(SealedObject)objectInput.readObject();
Test=(Test)sealedObject.getObject(密码);
System.out.println(test.variables.get(“Name”);
}
}
情况
newvariablemap(){{
放置(“名称”、“Furze”);
}}
创建匿名内部类(类的子类VariableMap
)并创建其对象
类和对象都是在同一位置创建的
它仍然是可序列化的
问题 当您注释它时,类定义本身消失 这将导致前面提到的
ClassNotFoundException
解决
序列化
。实现您自己的数据存储机制序列化
,请避免使用双大括号初始化test\u old
way)。然而,这是一个临时解决方案,也是一种糟糕的做法。这是混乱的,不可能记住。这也是将来出现错误的可能原因newvariablemap(){{
放置(“名称”、“Furze”);
}}
创建匿名内部类(类的子类VariableMap
)并创建其对象
类和对象都是在同一位置创建的
它仍然是可序列化的
问题 当您注释它时,类定义本身消失 这将导致前面提到的
ClassNotFoundException
解决
序列化
。实现您自己的数据存储机制序列化
,请避免使用双大括号初始化test\u old
way)。然而,这是一个临时解决方案,也是一种糟糕的做法。这是混乱的,不可能记住。这也是将来出现错误的可能原因我认为您缺少以下答案,因为我将您的所有代码放在一个文件中,并且运行良好。@Pra