JavaRush /جاوا بلاگ /Random-UR /خلاصہ کلاسز اور انٹرفیس کے درمیان فرق

خلاصہ کلاسز اور انٹرفیس کے درمیان فرق

گروپ میں شائع ہوا۔
ہیلو! اس لیکچر میں ہم اس بارے میں بات کریں گے کہ خلاصہ کلاسز انٹرفیس سے کس طرح مختلف ہیں اور عام خلاصہ کلاسوں کے ساتھ مثالوں کو دیکھیں گے۔ خلاصہ کلاسز اور انٹرفیس کے درمیان فرق - 1ہم نے ایک خلاصہ کلاس اور انٹرفیس کے درمیان فرق کے لیے ایک الگ لیکچر وقف کیا، کیونکہ موضوع بہت اہم ہے۔ مستقبل کے 90% انٹرویوز میں آپ سے ان تصورات کے درمیان فرق کے بارے میں پوچھا جائے گا۔ اس لیے جو کچھ آپ پڑھتے ہیں اسے ضرور سمجھ لیں، اور اگر آپ کسی چیز کو پوری طرح سمجھ نہیں پا رہے ہیں تو اضافی ذرائع پڑھیں۔ لہذا، ہم جانتے ہیں کہ خلاصہ کلاس کیا ہے اور انٹرفیس کیا ہے۔ اب آئیے ان کے اختلافات کو دیکھتے ہیں۔
  1. ایک انٹرفیس صرف رویے کی وضاحت کرتا ہے۔ اسے کوئی نصیب نہیں ہے۔ لیکن تجریدی طبقے کی ایک حالت ہوتی ہے: یہ دونوں کو بیان کرتی ہے۔

    آئیے مثال کے طور پر ایک خلاصہ کلاس Birdاور انٹرفیس لیتے ہیں Flyable:

    public abstract class Bird {
       private String species;
       private int age;
    
       public abstract void fly();
    
       public String getSpecies() {
           return species;
       }
    
       public void setSpecies(String species) {
           this.species = species;
       }
    
       public int getAge() {
           return age;
       }
    
       public void setAge(int age) {
           this.age = age;
       }
    }

    آئیے ایک برڈ کلاس Mockingjay(موکنگجے) بنائیں اور اس سے وارث کریں Bird:

    public class Mockingjay extends Bird {
    
       @Override
       public void fly() {
           System.out.println("Fly, birdie!");
       }
    
       public static void main(String[] args) {
    
           Mockingjay someBird = new Mockingjay();
           someBird.setAge(19);
           System.out.println(someBird.getAge());
       }
    }

    جیسا کہ آپ دیکھ سکتے ہیں، ہم خلاصہ کلاس کی حالت تک آسانی سے رسائی حاصل کر سکتے ہیں - اس کے متغیرات species(قسم) اور age(عمر)۔

    لیکن اگر ہم انٹرفیس کے ساتھ ایسا کرنے کی کوشش کریں تو تصویر مختلف ہوگی۔ ہم اس میں متغیرات شامل کرنے کی کوشش کر سکتے ہیں:

    public interface Flyable {
    
       String species = new String();
       int age = 10;
    
       public void fly();
    }
    
    public interface Flyable {
    
       private String species = new String(); // error
       private int age = 10; // also an error
    
       public void fly();
    }

    ہم انٹرفیس کے اندر نجی متغیرات بھی نہیں بنا پائیں گے ۔ کیوں؟ کیونکہ پرائیویٹ موڈیفائر صارف سے نفاذ کو چھپانے کے لیے بنایا گیا تھا۔ لیکن انٹرفیس کے اندر کوئی عمل درآمد نہیں ہے: وہاں چھپانے کے لئے کچھ نہیں ہے۔

    انٹرفیس صرف رویے کو بیان کرتا ہے۔ اس کے مطابق، ہم انٹرفیس کے اندر گیٹرز اور سیٹرز کو لاگو کرنے کے قابل نہیں ہوں گے۔ یہ ایک انٹرفیس کی نوعیت ہے: اس کا مقصد سلوک سے نمٹنا ہے، ریاست سے نہیں۔

    Java8 نے پہلے سے طے شدہ انٹرفیس کے طریقے متعارف کرائے جن پر عمل درآمد ہوتا ہے۔ آپ ان کے بارے میں پہلے سے ہی جانتے ہیں، اس لیے ہم انہیں نہیں دہرائیں گے۔

  2. ایک تجریدی کلاس ان کلاسوں کو جوڑتی اور جوڑتی ہے جن کا آپس میں بہت گہرا تعلق ہوتا ہے۔ ایک ہی وقت میں، ایک ہی انٹرفیس کو کلاسوں کے ذریعہ لاگو کیا جاسکتا ہے جن میں کچھ بھی مشترک نہیں ہے۔

    آئیے پرندوں کے ساتھ اپنی مثال پر واپس آتے ہیں۔

    Birdاس کی بنیاد پر پرندے بنانے کے لیے ہماری تجریدی کلاس کی ضرورت ہے۔ صرف پرندے اور کوئی نہیں! یقیناً وہ مختلف ہوں گے۔

    خلاصہ کلاسز اور انٹرفیس کے درمیان فرق - 2

    انٹرفیس کے ساتھ Flyableسب کچھ مختلف ہے۔ یہ صرف اس کے نام کے مطابق رویے کی وضاحت کرتا ہے - "اڑنا". "اڑنا"، "اڑنے کے قابل" کی تعریف میں بہت سی ایسی چیزیں شامل ہیں جو ایک دوسرے سے متعلق نہیں ہیں۔

    خلاصہ کلاسز اور انٹرفیس کے درمیان فرق - 3

    یہ 4 ادارے کسی بھی طرح سے ایک دوسرے سے متعلق نہیں ہیں۔ میں کیا کہوں، ان میں سے سب بھی متحرک نہیں ہیں۔ تاہم، وہ تمام Flyableپرواز کے قابل ہیں.

    ہم تجریدی کلاس کا استعمال کرتے ہوئے ان کی وضاحت کرنے کے قابل نہیں ہوں گے۔ ان کی کوئی مشترکہ ریاست یا ایک جیسی فیلڈ نہیں ہے۔ ہوائی جہاز کی خصوصیت کے لیے، ہمیں ممکنہ طور پر "ماڈل"، "تیار کا سال" اور "مسافروں کی زیادہ سے زیادہ تعداد" کے شعبوں کی ضرورت ہوگی۔ کارلسن کے لیے، ان تمام مٹھائیوں کے لیے میدان ہیں جو اس نے آج کھائی ہیں، اور ان کھیلوں کی فہرست ہے جو وہ بچے کے ساتھ کھیلے گا۔ مچھر کے لیے...اوہ...ہمیں یہ تک نہیں معلوم...ہو سکتا ہے "جھنجھلاہٹ کی سطح"؟ :)

    اہم بات یہ ہے کہ ہم تجریدی کلاس کا استعمال کرتے ہوئے انہیں بیان نہیں کر سکتے۔ وہ بہت مختلف ہیں۔ لیکن ایک عام رویہ ہے: وہ اڑ سکتے ہیں۔ انٹرفیس دنیا کی ہر اس چیز کو بیان کرنے کے لیے مثالی ہے جو اُڑ سکتی ہے، تیر سکتی ہے، چھلانگ لگا سکتی ہے یا کوئی اور سلوک کر سکتی ہے۔

  3. کلاسز جتنے چاہیں انٹرفیس نافذ کر سکتی ہیں، لیکن وہ صرف ایک کلاس سے وراثت میں مل سکتی ہیں۔

    ہم پہلے ہی اس کے بارے میں ایک سے زیادہ بار بات کر چکے ہیں۔ جاوا میں ایک سے زیادہ وراثت نہیں ہے، لیکن ایک سے زیادہ عمل درآمد ہے۔ یہ نقطہ جزوی طور پر پچھلے ایک سے فالو کرتا ہے: ایک انٹرفیس بہت سی مختلف کلاسوں کو جوڑتا ہے جن میں اکثر کچھ بھی مشترک نہیں ہوتا ہے، اور ایک تجریدی کلاس ان کلاسوں کے گروپ کے لیے بنائی جاتی ہے جو ایک دوسرے کے بہت قریب ہوتے ہیں۔ لہذا، یہ منطقی ہے کہ آپ صرف ایک ایسی کلاس سے وارث ہوسکتے ہیں۔ ایک تجریدی کلاس "ایک ہے" تعلق کو بیان کرتی ہے۔

معیاری ان پٹ اسٹریم اور آؤٹ پٹ اسٹریم انٹرفیس

ہم پہلے ہی ان پٹ اور آؤٹ پٹ کو اسٹریم کرنے کے لیے ذمہ دار مختلف کلاسوں سے گزر چکے ہیں۔ آئیے دیکھتے ہیں InputStreamاور OutputStream. عام طور پر، یہ انٹرفیس نہیں بلکہ حقیقی تجریدی کلاسز ہیں۔ اب آپ جانتے ہیں کہ وہ کیا ہیں، تو ان کے ساتھ کام کرنا بہت آسان ہو جائے گا :) InputStream- یہ ایک خلاصہ کلاس ہے جو بائٹ ان پٹ کے لیے ذمہ دار ہے۔ جاوا میں کلاسوں کا ایک سلسلہ ہے جو وراثت میں ملتا ہے InputStream۔ ان میں سے ہر ایک کو مختلف ذرائع سے ڈیٹا حاصل کرنے کے لیے ترتیب دیا گیا ہے۔ چونکہ InputStreamیہ والدین ہے، یہ ڈیٹا اسٹریمز کے ساتھ آسانی سے کام کرنے کے لیے کئی طریقے فراہم کرتا ہے۔ ہر بچے کے پاس یہ طریقے ہیں InputStream:
  • int available()پڑھنے کے لیے دستیاب بائٹس کی تعداد لوٹاتا ہے۔
  • close()ان پٹ سورس کو بند کرتا ہے؛
  • int read()سٹریم میں اگلے دستیاب بائٹ کی عددی نمائندگی لوٹاتا ہے۔ اگر سلسلہ کے اختتام تک پہنچ جاتا ہے، نمبر -1 واپس آ جائے گا؛
  • int read(byte[] buffer)بفر میں بائٹس کو پڑھنے کی کوشش کرتا ہے، پڑھے جانے والے بائٹس کی تعداد واپس کرتا ہے۔ جب یہ فائل کے آخر تک پہنچ جاتا ہے، تو یہ -1 لوٹتا ہے۔
  • int read(byte[] buffer, int byteOffset, int byteCount)بائٹس کے بلاک کا حصہ پڑھتا ہے۔ اس وقت استعمال کیا جاتا ہے جب اس بات کا امکان ہو کہ ڈیٹا بلاک مکمل طور پر نہیں بھرا تھا۔ جب یہ فائل کے آخر تک پہنچ جاتا ہے، تو -1 لوٹاتا ہے۔
  • long skip(long byteCount)skips byteCount، ان پٹ کا ایک بائٹ، نظر انداز کیے گئے بائٹس کی تعداد واپس کرنا۔
میں آپ کو مشورہ دیتا ہوں کہ طریقوں کی مکمل فہرست کا مطالعہ کریں ۔ درحقیقت ایک درجن سے زیادہ جانشین کلاسز ہیں۔ یہاں چند مثالیں ہیں:
  1. FileInputStream: سب سے عام قسم InputStream۔ فائل سے معلومات کو پڑھنے کے لیے استعمال کیا جاتا ہے۔
  2. StringBufferInputStream: ایک اور مفید قسم InputStream۔ یہ ایک تار کو ان پٹ ڈیٹا سٹریم میں بدل دیتا ہے InputStream۔
  3. BufferedInputStream: بفر شدہ ان پٹ سٹریم۔ یہ اکثر کارکردگی کو بہتر بنانے کے لیے استعمال ہوتا ہے۔
کیا آپ کو یاد ہے جب ہم وہاں سے گزرے BufferedReaderاور کہا کہ ہمیں اسے استعمال کرنے کی ضرورت نہیں ہے؟ جب ہم لکھتے ہیں:
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in))
اسے استعمال کرنے کی ضرورت نہیں BufferedReader: InputStreamReaderیہ کام کرے گا۔ لیکن BufferedReaderیہ اسے زیادہ مؤثر طریقے سے کرتا ہے اور اس کے علاوہ، انفرادی حروف کے بجائے پوری لائنوں میں ڈیٹا پڑھ سکتا ہے۔ سب کچھ BufferedInputStreamایک جیسا ہے! کلاس ان پٹ ڈیوائس تک مسلسل رسائی کیے بغیر ان پٹ ڈیٹا کو ایک خاص بفر میں جمع کرتی ہے۔ آئیے ایک مثال دیکھتے ہیں:
import java.io.BufferedInputStream;
import java.io.FileInputStream;
import java.io.InputStream;

public class BufferedInputExample {

   public static void main(String[] args) throws Exception {
       InputStream inputStream = null;
       BufferedInputStream buffer = null;

       try {

           inputStream = new FileInputStream("D:/Users/UserName/someFile.txt");

           buffer = new BufferedInputStream(inputStream);

           while(buffer.available()>0) {

               char c = (char)buffer.read();

               System.out.println("Character was read" + c);
           }
       } catch(Exception e) {

           e.printStackTrace();

       } finally {

           inputStream.close();
           buffer.close();
       }
   }
}
اس مثال میں، ہم ایک فائل سے ڈیٹا پڑھ رہے ہیں جو کمپیوٹر پر "D:/Users/UserName/someFile.txt" پتے پر موجود ہے ۔ ہم 2 اشیاء بناتے ہیں - FileInputStreamاور BufferedInputStreamاس کے "ریپر" کے طور پر۔ اس کے بعد، ہم فائل سے بائٹس پڑھتے ہیں اور انہیں حروف میں تبدیل کرتے ہیں۔ اور اسی طرح فائل ختم ہونے تک۔ جیسا کہ آپ دیکھ سکتے ہیں، یہاں کچھ بھی پیچیدہ نہیں ہے۔ آپ اس کوڈ کو کاپی کرسکتے ہیں اور اسے کسی حقیقی فائل پر چلا سکتے ہیں جو آپ کے کمپیوٹر پر محفوظ ہے :) کلاس OutputStreamایک خلاصہ کلاس ہے جو بائٹ اسٹریم آؤٹ پٹ کی وضاحت کرتی ہے۔ InputStreamجیسا کہ آپ پہلے ہی سمجھ چکے ہیں، یہ 'a' کا اینٹی پوڈ ہے ۔ یہ اس بات کی ذمہ دار نہیں ہے کہ ڈیٹا کہاں سے پڑھا جائے، بلکہ اسے کہاں بھیجنا ہے ۔ جیسے InputStream، یہ خلاصہ کلاس تمام اولادوں کو آسان کام کے لیے طریقوں کا ایک گروپ فراہم کرتا ہے:
  • int close()آؤٹ پٹ سٹریم بند کرتا ہے؛
  • void flush()تمام آؤٹ پٹ بفرز کو صاف کرتا ہے؛
  • abstract void write (int oneByte)آؤٹ پٹ اسٹریم پر 1 بائٹ لکھتا ہے۔
  • void write (byte[] buffer)آؤٹ پٹ اسٹریم پر بائٹس کی ایک صف لکھتا ہے۔
  • void write (byte[] buffer, int offset, int count)پوزیشن آفسیٹ سے شروع ہونے والی صف سے گنتی بائٹس کی ایک رینج لکھتا ہے۔
یہاں کلاس کی کچھ اولادیں ہیں OutputStream:
  1. DataOutputStream. ایک آؤٹ پٹ سٹریم جس میں معیاری جاوا ڈیٹا کی قسمیں لکھنے کے طریقے شامل ہیں۔

    جاوا کی ابتدائی اقسام اور تار لکھنے کے لیے ایک بہت ہی آسان کلاس۔ یقیناً آپ بغیر وضاحت کے تحریری کوڈ کو سمجھ جائیں گے:

    import java.io.*;
    
    public class DataOutputStreamExample {
    
       public static void main(String[] args) throws IOException {
    
           DataOutputStream dos = new DataOutputStream(new FileOutputStream("testFile.txt"));
    
           dos.writeUTF("SomeString");
           dos.writeInt(22);
           dos.writeDouble(1.21323);
           dos.writeBoolean(true);
    
       }
    }

    اس میں ہر قسم کے لیے الگ الگ طریقے ہیں - writeDouble(), writeLong(), writeShort()اور اسی طرح۔

  2. کلاس FileOutputStream _ ڈسک پر موجود فائل میں ڈیٹا بھیجنے کا طریقہ کار نافذ کرتا ہے۔ ویسے، ہم اسے پچھلی مثال میں استعمال کر چکے ہیں، کیا آپ نے نوٹس لیا؟ ہم نے اسے ڈیٹا آؤٹ پٹ اسٹریم کے اندر منتقل کیا، جس نے "ریپر" کے طور پر کام کیا۔

  3. BufferedOutputStream. بفر شدہ آؤٹ پٹ سٹریم۔ کچھ بھی پیچیدہ نہیں، جوہر وہی ہے جو BufferedInputStream(یا BufferedReader'a) میں ہے۔ معمول کی ترتیب وار ڈیٹا ریکارڈنگ کے بجائے، ایک خاص "اسٹوریج" بفر کے ذریعے ریکارڈنگ کا استعمال کیا جاتا ہے۔ بفر کا استعمال کرتے ہوئے، آپ ڈیٹا کی منزل تک راؤنڈ ٹرپس کی تعداد کو کم کر سکتے ہیں اور اس طرح کارکردگی کو بہتر بنا سکتے ہیں۔

    import java.io.*;
    
    public class DataOutputStreamExample {
    
       public static void main(String[] args) throws IOException {
    
           FileOutputStream outputStream = new FileOutputStream("D:/Users/Username/someFile.txt");
           BufferedOutputStream bufferedStream = new BufferedOutputStream(outputStream);
    
           String text = "I love Java!"; // we will convert this string into an array of bytes and write it to a file
    
           byte[] buffer = text.getBytes();
    
           bufferedStream.write(buffer, 0, buffer.length);
           bufferedStream.close();
       }
    }

    ایک بار پھر، آپ خود اس کوڈ کے ساتھ "کھیل" سکتے ہیں اور چیک کر سکتے ہیں کہ یہ آپ کے کمپیوٹر پر حقیقی فائلوں پر کیسے کام کرے گا۔

آپ وارثوں کے بارے میں مواد میں بھی پڑھ سکتے ہیں " InputStreamان پٹ /آؤٹ پٹ سسٹم "۔ اوہ ، اور ہمارا ایک الگ لیکچر بھی ہوگا، اس لیے پہلے جاننے والوں کے لیے ان کے بارے میں کافی معلومات موجود ہیں۔ بس! ہم امید کرتے ہیں کہ آپ انٹرفیس اور خلاصہ کلاسوں کے درمیان فرق کو اچھی طرح سمجھتے ہیں اور کسی بھی سوال کا جواب دینے کے لیے تیار ہیں، یہاں تک کہ ایک مشکل سوال بھی :) OutputStreamFileInputStreamFileOutputStreamBufferedInputStream
تبصرے
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION