2012-04-19 36 views
21

Nhiều sách/bài báo tôi đã đọc về chủ đề này, cũng như một chương trình nhỏ mà tôi đã viết bằng cách sử dụng 'Không an toàn', chỉ ra rằng các mảng 1-d trong Java luôn luôn tiếp giáp trong bộ nhớ. Vì vậy, nó được quyết định bởi JLS hay nó là một quy ước thực hiện? Câu hỏi được yêu cầu xác nhận chỉ dẫn này.Java: là mảng 1-d luôn luôn tiếp giáp trong bộ nhớ?

Trả lời

15

Không, đặc tả JVM không có bất kỳ sự bảo đảm như: http://docs.oracle.com/javase/specs/jvms/se5.0/html/Concepts.doc.html#16446

Trên thực tế nó có lẽ là trường hợp nhưng bạn cũng có không đảm bảo về kích thước chữ.

không an toàn không phải là một lớp Java tiêu chuẩn, vì vậy nếu chương trình của bạn sử dụng này, sau đó nó không phải là cầm tay anyway ...

10

Vì không có cách nào thực sự để tương tác với địa chỉ bộ nhớ trong Java, nó cũng không được xác định trong đặc tả cách bố cục của đối tượng trong bộ nhớ trông như thế nào.

Lưu ý rằng việc sử dụng Unsafe khá nhiều tự động có nghĩa là bạn đang đi dạo bên ngoài vương quốc của thông số kỹ thuật.

Điều đó đang được nói, tôi muốn liên tưởng rằng hầu hết các triển khai JVM làm trên thực tế sử dụng bố cục tuyến tính cho mảng (một chiều).

3

Cho rằng nhiều JVM có một yêu cầu rằng các đống là liên tục trong bộ nhớ Tôi nghĩ chắc nó họ sẽ đặt một mảng nguyên thủy 1d ở những nơi khác nhau trong bộ nhớ.

Đối tượng được tham chiếu bởi đối tượng [] dường như không liên tục trong bộ nhớ và ngay cả khi chúng có thể được sắp xếp lại mà không cần cảnh báo.

Lưu ý: Sử dụng Không an toàn, bạn có thể đọc tham chiếu trong một mảng dưới dạng các giá trị int để xem chúng là gì trước và sau GC. Một số JVM sử dụng tài liệu tham khảo 64 bit yêu cầu tài liệu tham khảo dài 32-bit (ngay cả đối với các JVM 64 bit)

+2

đã đồng ý, nhưng bản thân mảng sẽ tiếp giáp, phải không? một cái gì đó như thế này: 1000-> aa, 1001-> bb, 1002-> cd vv – shrini1000

+1

Tôi mong đợi các tài liệu tham khảo nên được lưu trữ liên tục (nhưng tôi không tin rằng nó được chỉ định ở bất cứ nơi nào) Điều này tương tự như thực tế là Spec không nói tính toán tham chiếu sẽ không được sử dụng cho GC trong bất kỳ JVM nào, nhưng AFAIK không thực hiện. –

+3

@ shrini1000 nếu heap không phải là một khối tiếp giáp của bộ nhớ ảo, sau đó một mảng spannig hai mảnh sẽ không có bố trí tiếp giáp. Mặt khác, heap được tiếp giáp ngụ ý không có gì về mảng là quá, có thể chỉ gián tiếp làm cho nó nhiều khả năng kể từ khi các ràng buộc thiết kế GC sẽ là tương tự. –

8

Tôi muốn làm mới câu hỏi này với những gì The Java Language Specification, Java SE 8 Edition (JLS)The Java Virtual Machine Specification, Java SE 8 Edition (JVMS) đang nói về nó.

Chúng ta phải lựa chọn để trả lời cho câu hỏi này:

  1. gì khó khăn được áp dụng đối với việc triển khai JVM. Đây là phương pháp đáng tin cậy nhất bởi vì việc thực hiện bất kỳ đặc tả nào vốn đã giả định là "Mọi thứ không bị cấm được cho phép" nguyên tắc.
  2. gì hầu hết các trường JVM đề nghị hợp lý

Tôi sẽ chỉ ra những hạn chế đặc điểm kỹ thuật.

Nếu chúng ta nhìn vào Chương 10 Mảng của JLS (và bất kỳ chương khác của JLSJVM liên quan đến mảng), chúng tôi không thể tìm thấy bất kỳ đề cập đến những hạn chế bố trí bộ nhớ áp đặt để mảng. Vì vậy, nó chắc chắn có nghĩa là mảng có thể không liên tục.

Hơn nữa, JLS nói rằng mảng là Objects:

Chương 10 Mảng.

Trong ngôn ngữ lập trình Java, mảng là đối tượng (§4.3.1), được tự động tạo ra, và có thể được gán cho biến kiểu Object (§4.3.2). Tất cả các phương thức của đối tượng lớp có thể là được gọi trên một mảng.
...

4.3.1. Các đối tượng.

Đối tượng là đối tượng lớp hoặc một mảng. (Và Array là Object)

Và cùng lúc JVM nói rằng các đối tượng và mảng được lưu trữ trên heap:

2.5.3. Heap

Máy ảo Java có một đống được chia sẻ giữa tất cả các luồng máy ảo Java. Vùng heap là vùng dữ liệu thời gian chạy từ đó bộ nhớ cho tất cả các cá thể lớp và mảng được cấp phát.

Nhưng JVM không buộc bộ nhớ heap được liên tục:

2.5.3. Heap

... Bộ nhớ cho heap không cần phải liên tục.

Vì tất cả các mảng được lưu trữ trong heap và heap có thể không liên tục, nó tuân theo các mảng cũng có thể không liên tục.

+0

Chỉ cần lưu ý: [Khi nào định dạng mã được sử dụng cho văn bản không phải mã?] (Http://meta.stackoverflow.com/a/254995) :). – Tom

+0

Tôi sẽ làm các trích dẫn tương tự từ thông số chính thức như thế nào? Tôi muốn cô lập chúng từ các văn bản khác để đọc tốt hơn. – likern

+0

Hãy nhớ sự khác biệt giữa "định dạng mã" và "blockquote". Các từ như "JLS", "JVMS" và "Chương 10. Mảng." không có mã và phải được định dạng như vậy :). Các dấu ngoặc kép là chính xác. – Tom

Các vấn đề liên quan