30/09/2018, 23:37

Không ghi được Object vào File

Trong quá trình làm phương thức viết dữ liêu vào file nó bị báo lỗi , em cần lưu đối tượng vào flie . Em biết lỗi ở đó nhưng không biết sửa như thế nào mong mấy anh giúp đỡ.

    @Override
    public void writeToFile() {
        Customer c = new Customer(ccode, cus_name);        // bi loi o cho nay ne may anh.
        try {
            FileOutputStream fos = new FileOutputStream("A:\HK5\CSDL\test.txt");
            ObjectOutputStream oos = new ObjectOutputStream(fos);
            
            oos.writeObject(c);
            oos.close();
            fos.flush();
            fos.close();
            System.out.println("Save file successful!");
        } catch (Exception ex) {
            System.out.println(ex);
        }
    }

public Customer readFromFile() {
        Customer c = new Customer();
        try {
            FileInputStream fis = new FileInputStream("A:\HK5\CSDL\test.txt");
            ObjectInputStream ois = new ObjectInputStream(fis);
            Object obj = ois.readObject();
            c = (Customer) obj;
        } catch (Exception ex) {
            System.out.println(ex);
        }
        return c;
  }
Đỗ Trung Quân viết 01:52 ngày 01/10/2018

Bạn đã implement Serializable cho class Customer chưa?

Võ Phú Hữu viết 01:40 ngày 01/10/2018

Em làm rồi anh , nó vẫn không lưu được.

Đỗ Trung Quân viết 01:41 ngày 01/10/2018

Bạn up đoạn thông báo lỗi lên mình xem.

Võ Phú Hữu viết 01:48 ngày 01/10/2018

Error: java.io.NotSerializableException: java.util.Scanner

Error: at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1184)
at java.io.ObjectOutputStream.defaultWriteFields(ObjectOutputStream.java:1548)
at java.io.ObjectOutputStream.writeSerialData(ObjectOutputStream.java:1509)
at java.io.ObjectOutputStream.writeOrdinaryObject(ObjectOutputStream.java:1432)
at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1178)
at java.io.ObjectOutputStream.writeObject(ObjectOutputStream.java:348)
at Assignment01.Customer.writeToFile(Customer.java:141)
at Assignment01.MainApp.main(MainApp.java:55)

Đỗ Trung Quân viết 01:42 ngày 01/10/2018

Error: java.io.NotSerializableException: java.util.Scanner

Vì em không up class Customer nên anh đoán là trong đó có 1 field em sử dụng Scanner để input. Scanner không thể Serialization.

Võ Phú Hữu viết 01:52 ngày 01/10/2018

Dạ đúng rồi đó anh, em đang dùng Scanner để đễ nhập dữ liệu vào. Nếu vậy thì em phải làm sửa nó như thế nào hả anh

Đỗ Trung Quân viết 01:44 ngày 01/10/2018

Có 2 cách:
1 : Em sửa khái báo biến Scanner bằng cách thêm từ khóa transient (tạm thời). Nó sẽ thông báo cái biến Scanner đó sẽ không được Serialization

   private transient Scanner input;

2 : Đơn giản hơn là chỉ dùng nó như 1 biến local

Võ Phú Hữu viết 01:50 ngày 01/10/2018

Dạ cám ơn anh, mà khi em write to flie thì nó dữ liệu nó bị mã hóa hay sao ấy.

Đỗ Trung Quân viết 01:39 ngày 01/10/2018

Ừ, vì em đã triển khai serializable

Võ Phú Hữu viết 01:54 ngày 01/10/2018

Oh thì ra là vậy, hihi . Vậy khi đọc dữ liệu từ file lên nó không hiển thị anh ơi.

Đỗ Trung Quân viết 01:50 ngày 01/10/2018

Vậy khi đọc dữ liệu từ file lên nó không hiển thị anh ơi.

Chắc em định hỏi nó có hiển thị đúng như cũ không? Có nhé. Đó là quá trình Deserialization

Võ Phú Hữu viết 01:38 ngày 01/10/2018

Dạ đúng rồi đó anh, em nghĩ nó sai ở dòng
Customer c = new Customer(); thì phải.

Đỗ Trung Quân viết 01:46 ngày 01/10/2018

Up lỗi lên anh mới biết sai ở đâu chứ. Anh có thấy hết code của em đâu

Võ Phú Hữu viết 01:53 ngày 01/10/2018

Nó không có báo lỗi anh ah. Chỉ là không hiển thị được dữ liệu từ file thôi.

Đỗ Trung Quân viết 01:52 ngày 01/10/2018

Em có làm gì đâu mà nó hiển thị. Em sửa lại code như này xem

        Customer c;
        try {
            FileInputStream fis = new FileInputStream("A:\\HK5\\CSDL\\test.txt");
            ObjectInputStream ois = new ObjectInputStream(fis);
            c = (Customer ) ois.readObject();
            System.out.println(c.toString());
            ois.close();
        } catch (Exception ex) {
            System.out.println(ex);
        }
Võ Phú Hữu viết 01:41 ngày 01/10/2018

Sau khi em làm xong, thì nó có đọc dữ liệu nhưng chỉ hiển thị dữ liệu cuối em nhập thôi.

public void readFromFile() {
        Customer c;
        try {
            FileInputStream fis = new FileInputStream("A:\\HK5\\CSDL\\test.txt");
            ObjectInputStream ois = new ObjectInputStream(fis);
            
            c = (Customer) ois.readObject();
            System.out.println("-->" + "[" + cus.ccode + "," + cus.cus_name + "]");
        } catch (Exception ex) {
            System.out.println(ex);
        }
    }
Đỗ Trung Quân viết 01:41 ngày 01/10/2018

thì nó có đọc dữ liệu nhưng chỉ hiển thị dữ liệu cuối em nhập thôi.

Bởi vì mỗi lần em ghi/đọc object ra file code của em sẽ ghi lại object đó. Vì vây chỉ có thể đọc được 1 object cuối cùng.
Anh suggest 1 cách (chả hình dung ra từ tiếng việt nào cho dễ =)).
Em nên ghi và đọc object ra file theo List, ArrayList<'Customer>() hoặc gì đó.

Võ Phú Hữu viết 01:47 ngày 01/10/2018

Dạ đúng rồi đó anh. Hiện tại em đang làm Linked List nên không biết sử dụng nó như thế nào. Em gặp vấn đề đọc và ghi dữ liệu nên em đang tìm ra vấn đề.
Đây là code của em:

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.util.Scanner;

/**
 *
 * @author magen
 */
public class Customer implements ICusPro, Serializable {         //inheriting interfaces ICusPro,Serializable

    public String ccode;
    public String cus_name;

    Customer next;              // reference to the subsequent node in the list

    Customer head;              // head node of the list
    Customer tail;              // tail node of the list

    Customer cus;               //Create a variable
    transient Scanner sa = new Scanner(System.in);

    public String getCcode() {
        return ccode;
    }

    public void setCcode(String ccode) {
        this.ccode = ccode;
    }

    public String getCus_name() {
        return cus_name;
    }

    public void setCus_name(String cus_name) {
        this.cus_name = cus_name;
    }

    public Customer() {
        head = null;
        tail = null;
    }

    public Customer(String id, String name) {
        this.ccode = id;
        this.cus_name = name;
    }

    public boolean isEmpty() {
        return (head == null);
    }

    //Create new Customer
    @Override
    public void addNew() {
        cus = new Customer();               //create a new element
        System.out.print("Enter code: ");
        this.ccode = sa.nextLine();
        cus.setCcode(ccode);
        System.out.print("Enter name: ");
        this.cus_name = sa.nextLine();
        cus.setCus_name(cus_name);

        cus.next = head;
        head = cus;

    }

    @Override
    public void displayData() {
        if (isEmpty()) {        //List no elements
            System.out.println("No elements on the list!");
        } else {
            Customer c = head;
            while (c != null) {
                System.out.print("-->" + "[" + c.ccode + "," + c.cus_name + "]");
                c = c.next;
            }
            System.out.println("");
        }
    }

    @Override
    public void deleteByCode() {                 //Delete Customer by code
        System.out.println("Enter code: ");
        String code = sa.nextLine();
        head = deleteByCode(head, code);
        System.out.println("Delete successful!");
    }

    public Customer deleteByCode(Customer node, Object code) {
        if (node == null) {               //if node is null
            return node;
        } else if (node.ccode.equals(code)) {        //test code equal node.code
            return node.next;
        } else {
            node.next = deleteByCode(node.next, code);
        }
        return node;
    }

    @Override
    public boolean searchByCode() {
        if (head == null) {
            return false;
        } else {
            System.out.println("Enter code: ");
            Object code = sa.nextLine();
            cus = head;
            while (cus != null) {
                if (cus.getCcode().equals(code)) {
                    System.out.println("Found: " + "-->" + "[" + cus.ccode + "," + cus.cus_name + "]");
                    return true;
                }
                cus = cus.next;
            }
        }
        return false;
    }

    @Override
    public void writeToFile() {
        Customer c = new Customer(ccode, cus_name);
        try {
            FileOutputStream fos = new FileOutputStream("A:\\HK5\\CSDL\\test.txt");
            ObjectOutputStream oos = new ObjectOutputStream(fos);
            
            oos.writeObject(c);
            oos.close();
            fos.close();
            System.out.println("Save file successful!");
        } catch (Exception ex) {
            ex.printStackTrace();
        }
    }

    public void readFromFile() {
        try {
            FileInputStream fis = new FileInputStream("A:\\HK5\\CSDL\\test.txt");
            ObjectInputStream ois = new ObjectInputStream(fis);
            
            cus = (Customer) ois.readObject();
            System.out.println("-->" + "[" + cus.ccode + "," + cus.cus_name + "]");
            ois.close();
        } catch (Exception ex) {
            System.out.println(ex);
        }
    }
Đỗ Trung Quân viết 01:40 ngày 01/10/2018

Trước khi anh chỉ em tiếp. Em nên Redesign(cấu trúc lại) class của em nhé.
Em không nên để hết tất cả vào 1 class như vậy
Nên làm theo mô hình MVC

  1. Class entity(Customer) chỉ chứa Constructor, get/set method + toString() or Equals()
  2. Các method read /write, search, delete nên để ra 1 class khác

Em xem code mẫu đọc file này. Anh viết ngay ở đây nên có thể sai cú pháp. Nhưng nội dung là đúng nhé

//method GetListCustomer() // đây là method readfile của em
  Customer c = null; // tạo 1 object customer
  LinkedList<Customer> customers = new .... // tạo 1 linkedlist lưu từng object khi đọc file
  while ((c= (Customer )ois.readObject()) != null) {
     customers .add(c);
  }
  return customers; // trả lisr về cho method ở dưới
//method display list customers 
public void Display(LinkedList list){ // list này là return từ hàm trên
     ->> hiển thị list
}

P/s: Anh phải đi nấu cơm :D. Ăn xong anh sẽ nói rõ hơn.

Võ Phú Hữu viết 01:50 ngày 01/10/2018

Cám ơn anh. Tại em đang làm bài tâp, yêu cầu bài tập là phải tự tạo Linked List không được sử dụng cái có sẵn, nên em không sử dụng ở trên có được không nữa

Bài liên quan
0