فرايند Erasure در Generics های جاوا چگونه اتفاق می‌افتد؟

+1 رأی
میانگین بازدید روزانه 7.35147 بازدید

لطفا به کد زیر دقت کنید:

class Test {

	public void f(Test test) {

	}

	public <E extends Test> void f(E e) {
		
	}

}

در کد بالا متدی که یک پارامتر عام مشخص می‌کند، در فرآیند Erasure خاص‌ترین نوع را در نظر می‌گیرد که همان کلاس Test است. بنابراین به دلیل اینکه دو متد فوق امضاهای یکسان دارند، با خطای کامپایل مواجه می‌شویم.

اما حالا به کد زیر توجه کنید:

class Test {

	public void f(Test test) {

	}

	public <E> void f(E e) {

	}

}

public class Main {

	public static void main(String[] args) {
		Test test = new Test();

		test.f(test);
		test.f(test);
	}

}

در کد فوق هیچ خطایی به وجود نمیاد. چرا؟

سوال 2 هفته قبل در تالار برنامه نویسی توسط Sina1993 (14 امتیاز)
ویرایش 2 هفته قبل توسط Saeed Zarinfam

2 جواب

+2 رأی
 
بهترین جواب

واضح است که در مثال اول  کامپایلر خطا می دهد چون E فقط می تواند از نوع Test و یا کلاس هایی که Test را extends می کنند باشد و این صراحتا به کامپایلر گفته شده اما در مثال دوم نوع E مشخص نیست و این دو نوع تعریف کاربردهای مختلفی دارد بعنوان نمونه شما در مثال اول چون نوع مشخص است می توانید به متد های کلاس Test دسترسی داشته باشید

public <E extends Test> void f(E e) {
   e.printTest();
}

پس دیگری نیازی به تعریف

 public void f(Test test) {
 test.printTest();
    }

ندارید

اما در مثال دوم شما فقط در دو صورت می توانید به متدها دسترسی داشته باشید با استفاده از reflection یا cast کردن به تایپ مورد نظر .

public <E> void f(E e) {
 if(e.getClass().equals(Test.class)
((Test)e).printTest();
    }

اما در این روش هر تایپی غیر از Test نیز می توانید به آن پاس کنید .

public <E> void f(E e) {
 if(e.getClass().equals(Test.class)
((Test)e).printTest();
 if(e.getClass().equals(Person.class)
((Person)e).printName();
    }

پس نتیجه می گیریم که دو مثالی که شما زدید دو چیز کاملا متفاوت است .

جواب 2 هفته قبل توسط jedlab (500 امتیاز)
انتخاب شده در 2 هفته قبل توسط Sina1993
+1 رأی
در قسمت اول به این دلیل خطا کامپایل گرفته میشه چون اگر کلاسی از Test ارث بری کرده باشه می تونه به کلاس Test تبدیل بشه لذا در زمان اجرا کمپایلر متوجه نمیشه که باید کدوم متد رو فراخونی کنه چون ورودی هر کدوم ورودی دیگر هم میتونه میشه...
جواب 2 هفته قبل توسط Amir Hossein Qasemi (10 امتیاز)
ویرایش 2 هفته قبل توسط Amir Hossein Qasemi

سوال های مشابه

0 رأی
0 جواب میانگین بازدید روزانه 0.0787 بازدید
0 رأی
1 جواب میانگین بازدید روزانه 0.21224 بازدید
+1 رأی
2 جواب میانگین بازدید روزانه 0.91,024 بازدید
سوال 3 سال قبل در تالار برنامه نویسی توسط sara_sheikhi (20 امتیاز)
+1 رأی
1 جواب میانگین بازدید روزانه 0.19313 بازدید
+1 رأی
1 جواب میانگین بازدید روزانه 0.09154 بازدید
+1 رأی
1 جواب میانگین بازدید روزانه 0.0586 بازدید
+1 رأی
1 جواب میانگین بازدید روزانه 0.2367 بازدید
0 رأی
1 جواب میانگین بازدید روزانه 0.09146 بازدید
0 رأی
2 جواب میانگین بازدید روزانه 0.38614 بازدید
0 رأی
0 جواب میانگین بازدید روزانه 0.0746 بازدید
کانال تلگرام جواب یاب
...