एक एब्स्ट्रैक्ट क्लास में इंस्टेंस मेथड्स हो सकते हैं जो डिफ़ॉल्ट व्यवहार लागू करते हैं। एक इंटरफेस केवल कॉन्स्टेंट्स और इंस्टेंस मेथड्स घोषित कर सकता है, लेकिन डिफ़ॉल्ट व्यवहार लागू नहीं कर सकता और सभी मेथड्स अंतर्निहित रूप से एब्स्ट्रैक्ट होते हैं। एक इंटरफेस के सभी मेंबर्स पब्लिक होते हैं और कोई कार्यान्वयन नहीं होता।
विस्तृत तुलना
| विशेषता | एब्स्ट्रैक्ट क्लास | इंटरफेस |
|---|---|---|
| कीवर्ड | abstract class | interface |
| मेथड्स | एब्स्ट्रैक्ट + कंक्रीट (कार्यान्वयन के साथ) | Java 7: केवल एब्स्ट्रैक्ट Java 8+: डिफ़ॉल्ट/स्टेटिक मेथड्स भी |
| फील्ड्स (वेरिएबल्स) | इंस्टेंस + स्टेटिक, कोई भी मॉडिफायर | केवल public static final (कॉन्स्टेंट्स) |
| कंस्ट्रक्टर | हां (सबक्लास द्वारा चेनिंग के लिए) | नहीं |
| इंस्टेंशिएशन | नहीं (लेकिन कंस्ट्रक्टर होता है) | नहीं |
| विरासत | extends (केवल एक) | implements (एकाधिक) |
| एक्सेस मॉडिफायर | कोई भी (private, protected, आदि) | मेथड्स अंतर्निहित रूप से public |
| स्थिति (State) | रख सकता है (इंस्टेंस वेरिएबल्स) | नहीं रख सकता (केवल कॉन्स्टेंट्स) |
| उद्देश्य | "IS-A" संबंध, कोड साझाकरण | "CAN-DO" क्षमता, अनुबंध |
कोड उदाहरण
एब्स्ट्रैक्ट क्लास
abstract class Animal {
// स्टेट (इंस्टेंस वेरिएबल)
protected String name;
protected int age;
// कंस्ट्रक्टर
public Animal(String name, int age) {
this.name = name;
this.age = age;
}
// कंक्रीट मेथड (कार्यान्वयन के साथ)
public void eat() {
System.out.println(name + " is eating");
}
// एब्स्ट्रैक्ट मेथड (कार्यान्वयन के बिना)
public abstract void makeSound();
// फाइनल मेथड (ओवरराइड नहीं किया जा सकता)
public final void sleep() {
System.out.println(name + " is sleeping");
}
}
class Dog extends Animal {
public Dog(String name, int age) {
super(name, age);
}
@Override
public void makeSound() {
System.out.println("Woof!");
}
}
इंटरफेस
interface Flyable {
// कॉन्स्टेंट्स (अंतर्निहित public static final)
int MAX_ALTITUDE = 10000;
// एब्स्ट्रैक्ट मेथड (अंतर्निहित public abstract)
void fly();
// डिफ़ॉल्ट मेथड (Java 8+)
default void land() {
System.out.println("Landing...");
}
// स्टेटिक मेथड (Java 8+)
static boolean canFly(String animalType) {
return !"penguin".equalsIgnoreCase(animalType);
}
}
class Bird implements Flyable {
@Override
public void fly() {
System.out.println("Flying high!");
}
// land() डिफ़ॉल्ट उपयोग कर सकता है या ओवरराइड कर सकता है
}
कब क्या उपयोग करें?
एब्स्ट्रैक्ट क्लास का उपयोग करें जब:
- क्लासेस के बीच कोड साझा करना हो (DRY सिद्धांत)
- सामान्य स्टेट (फील्ड्स) हो
- कंस्ट्रक्टर लॉजिक चाहिए
- टेम्पलेट मेथड पैटर्न लागू करना हो
- निकट से संबंधित क्लासेस हों (IS-A संबंध)
इंटरफेस का उपयोग करें जब:
- अनुबंध/क्षमता परिभाषित करना हो (CAN-DO)
- मल्टीपल इम्प्लीमेंटेशन संभव हो
- असंबंधित क्लासेस सामान्य व्यवहार साझा करें
- मल्टीपल इम्प्लीमेंटेशन की आवश्यकता हो
- API डिजाइन करना हो (पब्लिक कॉन्ट्रैक्ट)
संयोजन: दोनों का उपयोग
// बेस एब्स्ट्रैक्ट क्लास - सामान्य कोड/स्टेट
abstract class AbstractVehicle {
protected String brand;
protected int year;
public AbstractVehicle(String brand, int year) {
this.brand = brand;
this.year = year;
}
public abstract void start();
}
// इंटरफेस - क्षमताएं
interface Electric {
void charge();
default int getBatteryLevel() { return 100; }
}
interface Autonomous {
void enableAutopilot();
}
// कंक्रीट क्लास - दोनों का उपयोग
class Tesla extends AbstractVehicle implements Electric, Autonomous {
public Tesla(int year) {
super("Tesla", year);
}
@Override
public void start() { System.out.println("Silent start"); }
@Override
public void charge() { System.out.println("Charging..."); }
@Override
public void enableAutopilot() { System.out.println("Autopilot on"); }
}
निष्कर्ष: एब्स्ट्रैक्ट क्लास "क्या है" (IS-A) और कोड साझाकरण के लिए है। इंटरफेस "क्या कर सकता है" (CAN-DO) और अनुबंध के लिए है। आधुनिक Java में डिफ़ॉल्ट/स्टेटिक मेथड्स के साथ इंटरफेस अधिक शक्तिशाली हो गए हैं, लेकिन एब्स्ट्रैक्ट क्लास स्टेट और कंस्ट्रक्टर लॉजिक के लिए अभी भी आवश्यक हैं।