【问题标题】:Java - Serialization - Grabbing number of objectsJava - 序列化 - 抓取对象数量
【发布时间】:2014-07-29 13:11:54
【问题描述】:

Java - 序列化 - 抓取文件中的对象数量


我正在尝试从我的序列化文件中检索我的对象并将它们重新添加到我的文件中。似乎有一个问题,没有抛出异常,但是在运行我的方法时,我的控制台中没有打印任何内容。在继续之前是我的代码:

public boolean openCollection(){
        try {
            FileInputStream e = new FileInputStream("profiles.ser");
            ObjectInputStream inputStream = new ObjectInputStream(e);
            List<Profile> profiles = (List<Profile>) inputStream.readObject();

            //De-obscure
            for(Profile p : profiles){
                String unObcName = deobscure(p.getName()); //Original name
                String unObcSurname = deobscure(p.getSurname()); //Original surname
                String unObcUsername = deobscure(p.getUsername()); //Original username
                String unObcPassword = deobscure(p.getPassword()); //Original password

                p.setName(unObcName);
                p.setSurname(unObcSurname);
                p.setUsername(unObcUsername);
                p.setPassword(unObcPassword);

                //Debugging
                System.out.println("DE-OBSCURE - Profile name: " + p.getName() +"\n"+
                        "Profile surname: " + p.getSurname() +"\n"+
                        "Profile username: " + p.getUsername() +"\n"+
                        "Profile password: " + p.getPassword());
                this.profiles.add(p);
            }

        } catch (FileNotFoundException var3) {
            SwingUtilities.invokeLater(new Runnable() {
                @Override
                public void run() {
                    JOptionPane.showMessageDialog(null, "No profiles found, please create a profile!");
                    final CreateProfile createProfile = new CreateProfile();
                    createProfile.setVisible(true);
                }
            });
            return false;
        } catch (IOException var4) {
            var4.printStackTrace();
            JOptionPane.showMessageDialog(null, "IO Exception");
            return false;
        } catch (ClassNotFoundException var5) {
            var5.printStackTrace();
            JOptionPane.showMessageDialog(null, "Required class not found");
            return false;
        }
    return true;
}

这是序列化方法

 public void saveCollection(){

    //Obscure the data
    List<Profile> saveProfiles = new ArrayList<>();
    for(Profile p : profiles){
        String obcName = obscure(p.getName());
        String obcSurname = obscure(p.getSurname());
        String obcUsername = obscure(p.getUsername());
        String obcPassword = obscure(p.getPassword());

        p.setName(obcName);
        p.setSurname(obcSurname);
        p.setUsername(obcUsername);
        p.setPassword(obcPassword);

        //Debugging
        System.out.println("DEBUG - Profile name: " + p.getName() + "\n" +
                "Profile surname: " + p.getSurname() + "\n" +
                "Profile username: " + p.getUsername() + "\n" +
                "Profile password: " + p.getPassword());

        saveProfiles.add(p);
    }

    //Save it
    try {
        FileOutputStream e = new FileOutputStream("profiles.ser");
        ObjectOutputStream outputStream = new ObjectOutputStream(e);
        outputStream.writeObject(saveProfiles);
        outputStream.flush();
        outputStream.close();
    } catch (IOException var3) {
        var3.printStackTrace();
        JOptionPane.showMessageDialog(null, "Error. Cannot save database.");
    }

}

创建配置文件时,详细信息被正确隐藏,结果如下:

调试 - 配置文件名称:OBF:1u2a1toa1w8v1tok1u30

个人资料姓氏:OBF:1u2a1toa1w8v1tok1u30

个人资料用户名:OBF:1u2a1toa1w8v1tok1u30

个人资料密码:OBF:1u2a1toa1w8v1tok1u30

但是,当运行 openCollection() 时,控制台没有打印任何内容。

注意:个人资料详细信息都是“管理员”,这就是为什么所有数据看起来都一样

【问题讨论】:

  • 你是如何序列化的?
  • 没有检索对象数量的方法。这将与 stream 的性质相反。如果您想要该号码,则必须手动将其写入您的流中。
  • Eliot 我会将 saveCollection() 添加到原始帖子中。 @Holger我是这么认为的,我以前遇到的问题是 openCollection() 会像你说的那样继续向我抛出 EOFException 原因,没有直接的方法可以真正知道文件中有多少对象,所以 readObject () 会用完对象并抛出异常,我觉得这很烦人,不能让它一直在控制台中抛出异常
  • 你让你的生活变得困难。与其写列表的大小,然后写列表的每个元素,不如简单地写列表本身。阅读就像List&lt;Profile&gt; profiles = (List&lt;Profile&gt;) objectInputStream.readObject(); 一样简单,也就是说,如果你用writeObject() 写大小,你应该用readObject() 阅读它。 read() 只读取一个字节。
  • 好的,谢谢 JB,我会试试看效果如何

标签: java serialization


【解决方案1】:

检查了一段时间后,我发现问题只是我的去模糊方法。我现在已经对其进行了编辑并将其替换为以下内容:

/**
 * @param str Obscured String
 * @return Unobscured String
 */
private String deobscure(String s){
    if (s.startsWith(__OBFUSCATE)) s = s.substring(4);

    byte[] b = new byte[s.length() / 2];
    int l = 0;
    for (int i = 0; i < s.length(); i += 4)
    {
        if (s.charAt(i)=='U')
        {
            i++;
            String x = s.substring(i, i + 4);
            int i0 = Integer.parseInt(x, 36);
            byte bx = (byte)(i0>>8);
            b[l++] = bx;

        }
        else
        {
            String x = s.substring(i, i + 4);
            int i0 = Integer.parseInt(x, 36);
            int i1 = (i0 / 256);
            int i2 = (i0 % 256);
            byte bx = (byte) ((i1 + i2 - 254) / 2);
            b[l++] = bx;
        }
    }

    return new String(b, 0, l,StandardCharsets.UTF_8);
}

原始个人资料名称:“管理员”

隐藏的配置文件名称:“OBF:1npu1toa1w8v1tok1nsc

消除个人资料名称后:“管理员”

因此,该方法现在按预期工作。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-07-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多