Tôi đã vấp phải điều này trong khi tìm kiếm một con đường tốt hơn những gì tôi đã đến. Sau khi đọc các câu trả lời và thử chúng, tôi nghĩ rằng đáng để đăng những gì tôi đang làm vì các câu trả lời khác không cảm thấy ngắn gọn đối với tôi. Điều quan trọng đối với tôi là chỉ phải viết một lượng mã ngắn mỗi khi tôi thiết lập một giao diện mới. Tôi đã quyết định ...
Sử dụng một hàm deepCopy chung chung tùy chỉnh:
deepCopy = <T extends {}>(input: any): T => {
return JSON.parse(JSON.stringify(input));
};
Xác định giao diện của bạn
interface IX {
a: string;
b: any;
c: AnotherType;
}
... và xác định các giá trị mặc định trong một hằng số riêng biệt.
const XDef : IX = {
a: '',
b: null,
c: null,
};
Sau đó, init như thế này:
let x : IX = deepCopy(XDef);
Đó là tất cả những gì cần thiết ..
.. Tuy nhiên ..
Nếu bạn muốn tùy chỉnh khởi tạo bất kỳ phần tử gốc nào, bạn có thể sửa đổi hàm deepCopy để chấp nhận các giá trị mặc định tùy chỉnh. Hàm trở thành:
deepCopyAssign = <T extends {}>(input: any, rootOverwrites?: any): T => {
return JSON.parse(JSON.stringify({ ...input, ...rootOverwrites }));
};
Thay vào đó, có thể được gọi như thế này:
let x : IX = deepCopyAssign(XDef, { a:'customInitValue' } );
Bất kỳ cách sao chép sâu ưa thích nào khác sẽ hoạt động. Nếu chỉ cần một bản sao cạn thì Object.assign là đủ, loại bỏ nhu cầu về tiện ích deepCopyhoặc deepCopyAssignchức năng.
let x : IX = object.assign({}, XDef, { a:'customInitValue' });
Các vấn đề đã biết
- Nó sẽ không gán sâu trong chiêu bài này nhưng không quá khó để sửa đổi
deepCopyAssignđể lặp lại và kiểm tra các loại trước khi gán.
- Các hàm và tham chiếu sẽ bị mất bởi quá trình phân tích cú pháp / chuỗi ký tự. Tôi không cần những thứ đó cho nhiệm vụ của mình và OP cũng vậy.
- Giá trị init tùy chỉnh không được gợi ý bởi IDE hoặc loại được kiểm tra khi thực thi.