Giao diện trừu tượng Java


197

Hãy xem xét một ví dụ (biên dịch trong java)

public abstract interface Interface {
    public void interfacing();
    public abstract boolean interfacing(boolean really);
}

Tại sao cần có một giao diện được "khai báo" trừu tượng? Có các quy tắc khác áp dụng với một giao diện trừu tượng?


Cuối cùng: Nếu abstractđã lỗi thời, tại sao nó lại được đưa vào Java? Có một lịch sử cho giao diện trừu tượng?



5
Không phải là một bản sao xem xét phần " Cuối cùng: .... ".
aioobe

Câu hỏi liên quan này trích dẫn một ví dụ thực tế: stackoverflow.com/questions/4380796/
Kẻ

1
Và tại sao Eclipse lại thêm 'trừu tượng' theo mặc định khi bạn 'giải nén giao diện'?
ModdyFire

@ModdyFire, xin hãy giải thích?
Buhake Sindi

Câu trả lời:


447

Tại sao cần có một giao diện được "khai báo" trừu tượng?

Nó không thể.

public abstract interface Interface {
       \___.__/
           |
           '----> Neither this...

    public void interfacing();
    public abstract boolean interfacing(boolean really);
           \___.__/
               |
               '----> nor this, are necessary.
}

Các giao diện và phương thức của chúng được ngầm định abstractvà thêm phần bổ trợ đó không tạo ra sự khác biệt.

Có các quy tắc khác áp dụng với một giao diện trừu tượng?

Không, quy tắc tương tự được áp dụng. Phương thức phải được thực hiện bởi bất kỳ lớp thực hiện (cụ thể) nào.

Nếu trừu tượng là lỗi thời, tại sao nó được bao gồm trong Java? Có một lịch sử cho giao diện trừu tượng?

Câu hỏi thú vị. Tôi đã đào phiên bản đầu tiên của JLS và thậm chí ở đó có ghi "Công cụ sửa đổi này đã lỗi thời và không nên được sử dụng trong các chương trình Java mới" .

Được rồi, đào sâu hơn nữa ... Sau khi nhấn nhiều liên kết bị hỏng, tôi đã tìm được một bản sao của Thông số kỹ thuật gốc Oak 0.2 (hoặc "thủ công"). Tôi phải nói khá thú vị, và chỉ có 38 trang! :-)

Trong Phần 5, Giao diện, nó cung cấp ví dụ sau:

public interface Storing {
    void freezeDry(Stream s) = 0;
    void reconstitute(Stream s) = 0;
}

Và trong lề nó nói

Trong tương lai, phần "= 0" của các phương thức khai báo trong các giao diện có thể biến mất.

Giả sử =0đã được thay thế bởi abstracttừ khóa, tôi nghi ngờ rằng abstracttại một số điểm bắt buộc đối với các phương thức giao diện!


Bài viết liên quan: Java: Giao diện trừu tượng và phương thức giao diện trừu tượng


3
nhưng bản thân trừu tượng không phải là lỗi thời, hay? Nó đã lỗi thời đối với các giao diện nhưng vẫn có các lớp và phương thức trừu tượng.
dùng85421

Cảm ơn ;-) Tôi nghĩ rằng cuối cùng tôi đã đóng đinh nguồn gốc thậm chí cho phép abstracttrước các phương thức giao diện.
aioobe

13
Ồ Vì vậy, nó đã lỗi thời "theo thiết kế". Những nhà thiết kế JLS đó thực sự luôn sợ phá vỡ thứ gì đó, thậm chí phá vỡ những thứ không bao giờ được phát hành ... :-)
Lukas Eder

@aioobe, bạn phải là người thu thập dữ liệu web của Google mà chúng tôi không biết về ... lol
Buhake Sindi

18
Btw. "công khai" cũng không cần thiết đối với các phương thức trong khai báo giao diện ... chúng luôn được công khai.
rec

37

Không cần thiết, nó là tùy chọn, giống như publictrên các phương thức giao diện.

Xem JLS về điều này:

http://java.sun.com/docs/books/jls/second_edition/html/interfaces.doc.html

9.1.1.1 Giao diện trừu tượng Mọi giao diện đều hoàn toàn trừu tượng. Công cụ sửa đổi này đã lỗi thời và không nên được sử dụng trong các chương trình mới.

9.4 Tuyên bố phương pháp trừu tượng

[...]

Để tương thích với các phiên bản cũ hơn của nền tảng Java, điều đó được cho phép nhưng không được khuyến khích, như là một vấn đề về phong cách, chỉ định một cách thừa thãi công cụ sửa đổi trừu tượng cho các phương thức được khai báo trong các giao diện.

Nó được cho phép, nhưng không được khuyến khích mạnh mẽ như một vấn đề về phong cách, để chỉ định một cách thừa thãi công cụ sửa đổi công khai cho các phương thức giao diện.


7
đối với JLS: Được phép, nhưng không được khuyến khích, vì vấn đề về phong cách, viết một cách thừa thãi hai câu có cùng ý nghĩa và từ ngữ gần như chính xác cạnh nhau ...
n611x007

11

Không cần thiết phải khai báo giao diện trừu tượng.

Cũng giống như khai báo tất cả các phương thức công khai (mà chúng đã có nếu giao diện là công khai) hoặc trừu tượng (mà chúng đã có trong một giao diện) là không cần thiết.

Không ai ngăn cản bạn, mặc dù.

Những thứ khác bạn có thể nói rõ ràng, nhưng không cần phải:

  • gọi super () trên dòng đầu tiên của hàm tạo
  • extends Object
  • thực hiện các giao diện được kế thừa

Có các quy tắc khác áp dụng với một giao diện trừu tượng?

Một giao diện đã "trừu tượng". Áp dụng từ khóa đó một lần nữa hoàn toàn không có sự khác biệt.


2
Rõ ràng, các phương thức thậm chí là công khai nếu bản thân giao diện là gói riêng.
Thilo

7

Hãy nhận biết rằng trong mùa xuân nó có ý nghĩa học thuật. Giao diện trừu tượng là một cảnh báo cho nhà phát triển không sử dụng nó cho @Autowired. Tôi hy vọng rằng mùa xuân / nhật thực @Autowiredsẽ xem xét thuộc tính này và cảnh báo / thất bại về việc sử dụng như vậy.

Một ví dụ thực tế: @Service proxy trong @Transnational cho @Rep repository cần sử dụng các phương thức cơ bản giống nhau tuy nhiên họ nên sử dụng các giao diện khác nhau mở rộng giao diện trừu tượng này @Autowired. (Tôi gọi giao diện XXXSpec này)


Lượt truy cập tốt, tôi đã tìm kiếm một cách rộng rãi các mũi tiêm phiên không thụ động. Có lẽ tôi có thể sử dụng findbugs / checkstyle cho một quy tắc ....
Grim

3

Mọi giao diện đều ngầm trừu tượng.
Công cụ sửa đổi này đã lỗi thời và không nên được sử dụng trong các chương trình mới.

[Đặc tả ngôn ngữ Java - abstractGiao diện 9.1.1.1 ]

Cũng lưu ý rằng các phương thức thành viên giao diện là ngầm public abstract.
[Đặc tả ngôn ngữ Java - 9.2 Thành viên giao diện]

Tại sao những sửa đổi ngầm? Không có công cụ sửa đổi nào khác (thậm chí không phải là công cụ sửa đổi ' không có công cụ sửa đổi ) sẽ hữu ích ở đây, vì vậy bạn không nhất thiết phải nhập nó.


2

Nó không cần thiết. Đó là một sự ngớ ngẩn của ngôn ngữ.


2

Không cần thiết, vì các giao diện theo mặc định là trừu tượng vì tất cả các phương thức trong một giao diện đều trừu tượng.


-2

Một giao diện trừu tượng không quá dư thừa như mọi người dường như đang nói, trên lý thuyết ít nhất.

Một giao diện có thể được mở rộng, giống như một Class có thể. Nếu bạn thiết kế cấu trúc phân cấp Giao diện cho ứng dụng của mình, bạn cũng có thể có Giao diện 'Cơ sở', bạn sẽ mở rộng các Giao diện khác từ nhưng không muốn tự nó là Đối tượng.

Thí dụ:

public abstract interface MyBaseInterface {
    public String getName();
}

public interface MyBoat extends MyBaseInterface {
    public String getMastSize();
}

public interface MyDog extends MyBaseInterface {
    public long tinsOfFoodPerDay();
}

Bạn không muốn một Class triển khai MyBaseInterface, chỉ có hai giao diện khác là MMyDog và MyBoat, nhưng cả hai giao diện đều chia sẻ giao diện MyBaseInterface, vì vậy hãy có thuộc tính 'name'.

Tôi biết nó hơi hàn lâm, nhưng tôi nghĩ một số người có thể thấy nó thú vị. :-)

Nó thực sự chỉ là một 'điểm đánh dấu' trong trường hợp này, để báo hiệu cho những người thực hiện giao diện mà nó không được thiết kế để tự thực hiện. Tôi nên chỉ ra một trình biên dịch (Ít nhất là mặt trời / ora 1.6 tôi đã thử với nó) biên dịch một lớp thực hiện một giao diện trừu tượng.


3
Tôi tin rằng bạn hoàn toàn hiểu sai câu hỏi của tôi.
Buhake Sindi

3
Tôi không đồng ý với lý do này. Tôi nghĩ rằng mọi giao diện phải cung cấp một bộ chức năng hoàn toàn có thể sử dụng và do đó mọi giao diện đều có thể tự thực hiện. Ngoài ra, sẽ không có lý do gì để trình biên dịch từ chối biên dịch một lớp thực hiện một giao diện được khai báo rõ ràng là trừu tượng, bởi vì tất cả các giao diện đã hoàn toàn trừu tượng. Điều đó sẽ thay đổi hoàn toàn ý nghĩa của từ khóa "trừu tượng".
BladeCoder

-3

Vâng 'Giao diện trừu tượng' là một cấu trúc từ điển: http://en.wikipedia.org/wiki/Lexical_analysis .

Nó được yêu cầu bởi trình biên dịch, bạn cũng có thể viết interface.

Đừng quá chú trọng vào cấu trúc ngôn ngữ của ngôn ngữ vì họ có thể đã đặt nó ở đó để giải quyết một số sự mơ hồ biên dịch được gọi là trường hợp đặc biệt trong quá trình biên dịch hoặc để tương thích ngược, hãy cố gắng tập trung vào cấu trúc cốt lõi.

Bản chất của `giao diện là nắm bắt một số khái niệm trừu tượng (ý tưởng / suy nghĩ / tư duy bậc cao, v.v.) mà việc thực hiện có thể khác nhau ... đó là, có thể có nhiều triển khai.

Giao diện là một kiểu dữ liệu trừu tượng thuần túy đại diện cho các tính năng của Đối tượng mà nó đang nắm bắt hoặc đại diện.

Các tính năng có thể được đại diện bởi không gian hoặc theo thời gian. Khi chúng được biểu diễn bằng không gian (bộ nhớ lưu trữ), điều đó có nghĩa là lớp cụ thể của bạn sẽ triển khai một trường và phương thức / phương thức sẽ hoạt động trên trường đó hoặc theo thời gian, điều đó có nghĩa là nhiệm vụ thực hiện tính năng này hoàn toàn là tính toán (đòi hỏi nhiều đồng hồ cpu hơn để xử lý) để bạn có sự đánh đổi giữa không gian và thời gian để thực hiện tính năng.

Nếu lớp cụ thể của bạn không triển khai tất cả các tính năng, nó sẽ trở nên trừu tượng vì bạn đã thực hiện ý nghĩ hoặc ý tưởng hoặc tính trừu tượng của mình nhưng nó không hoàn thành, bạn chỉ định nó theo abstractlớp.

Một lớp cụ thể sẽ là một lớp / tập hợp các lớp sẽ ghi lại đầy đủ tính trừu tượng mà bạn đang cố gắng để nắm bắt lớp XYZ.

Vì vậy, mô hình là

Interface--->Abstract class/Abstract classes(depends)-->Concrete class

1
Câu trả lời này không trả lời câu hỏi của tôi cả. Ngoài ra "It seams like you are new to Java. Có thật không?
Buhake Sindi

"trừu tượng là lỗi thời"
Manish

(1) "trừu tượng đã lỗi thời" -> nếu họ loại bỏ nó và trình biên dịch ngừng nhận ra nó thì phiên bản mã nguồn trước đó sử dụng "giao diện trừu tượng" sẽ không biên dịch trong phiên bản mới hơn .. Họ cần duy trì khả năng tương thích ngược. Khi bạn xác định giao diện trừu tượng, ý nghĩa của từ khóa giao diện bị mắc kẹt cùng với "trừu tượng" là phiên bản sạch hơn nhiều, tuy nhiên đối với các lập trình viên có kinh nghiệm như bạn, họ đã cung cấp lối tắt "giao diện" .. câu hỏi của bạn tương tự như i = i + 1 == > i ++ .. sự lựa chọn là của bạn những gì bạn chọn: D
Manish

Nhìn vào câu trả lời được chấp nhận. Tôi biết abstractlà lỗi thời trong giao diện. Tôi muốn biết tại sao nó vẫn được chấp nhận và lịch sử đằng sau abstractgiao diện là gì. Bạn đang cho tôi một hướng dẫn Java 101 trên giao diện trừu tượng vs.
Buhake Sindi

Nó không phải là một cấu trúc từ vựng. Đây là cú pháp. Về mặt ngữ nghĩa nó là dư thừa. Nó không phải là 'yêu cầu của trình biên dịch'. Phần về không gian / thời gian chỉ là drivel. Không ai trong số những điều vô nghĩa này trả lời câu hỏi đã được hỏi. Không sử dụng định dạng mã cho văn bản không phải là mã.
Hầu tước Lorne
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.