در قسمت هفتم آموزش شی گرایی در ادامه مباحث چندریختی و overriding موضوعاتی چون چندریختی توسط اعضا virtual و override کردن عملگر ها را آموزش داده ایم.
این قابلیت زمانی مورد استفاده قرار میگیرد که مثلا بخواهیم یک متد یا پروپرتی یا هر عنصر دیگر درون کلاس ریشه را درون یکی از زیر کلاس ها که از سیستم وراثت استفاده کرده را کپی کنیم برای درک بیشتر به مثال زیر توجه کنید
class Test1 { public int Age = 10; public virtual void Declare() { if(Age<15) { Console.WriteLine("you are teen"); } } } class Bigger:Test1 { public override void Declare() { if(Age < 25) { Console.WriteLine("you are young"); } } }
همانگونه که در عبارات فوق مشاهده میکنید در بدنه کلاس اصلی یک متد ایجاد شده ولی از نوع virtual تا بتوان دقیقا از همین متد با همین نام و پارامتر در کلاس دیگر که از این کلاس ارث بری میکند استفاده کرد دلیل استفاده از این ویژگی نیز این است که کلاسی که از کلاس اصلی ارث بری میکند در واقع تمامی متدها و عناصر دیگر درون کلاس که به صورت public میباشد را به صورت ضمنی درون خود دارد پس امکان دوباره نویسی مثلا یک متد حال با بدنه متفاوت نیست به همین علت از عبارت virtual در کلاس اصلی استفاده میکنیم و در کلاس مشتق شده از ویژگی override استفاده میکنیم به این صورت که عبارت override را نوشته و سپس با زدن یک space میتوان تمامی عناصری که میتوان override کرد را دید حال عنصر مورد نظر که در این مثال متد Declare میباشد انتخاب میکنیم و بدنه متد را بنا به نیاز تغییر میدهیم.
میتوان پروپرتی را نیز بدین صورت virtual کرد
class Test1 { private int FirstField; public virtual int VirtualProp { get { return FirstField; } set { FirstField = value; } } } class Bigger:Test1 { private int SecondField; public override int VirtualProp { get{ return SecondField; } set{SecondField = value;} } }
در virtual کردن پروپرتی ها نیز مانند متدها باید در کلاس مشتق شده پروپرتی را override کرد به همان روش گفته شده و به این نکته توجه داشته باشید که در کلاس اصلی نتیجه پروپرتی درون فیلد FirstField قرار میگیرد درحالی که اگر از پروپرتی درون کلاس مشتق شد استفاده کنیم نتیجه درون فیلد SecondField قرار میگیرد.
میتوان عملگر هارا نیز override کرد به عبارت دیگر ما میدانیم که نتیجه int result=2+2 میشود result=4 و یا حتی برای الحاق دو رشته نیز میتوان از عملگر + استفاده کرد این بدین معنی است که خود کامپایلر میتواند تشخیص بدهد که علامت + که بین دو عدد یا دو رشته می آید باید چ عملی انجام دهد اما نمیتواند تشخیص دهد که زمانی که این عملگر یا هر عملگر دیگری بین دو شی از کلاس بیاید باید چه عملی انجام دهد.
برای فهماندن این مسیله به کامپایلر باید عملگر را override کرد بدین معنی که درون خود کلاس مشخص کرد که زمانی که عملگر برای شی از همان کلاس استفاده شد کامپایلر باید چه عملی انجام دهد.
مثال زیر جمع دو عدد اعشاری میباشد که قسمت صحیح واعشار آنرا جدا جمع کرده و نمایش میدهد
class Test1 { public int Real; public int i; public Test1(int real, int i) { this.Real = real; this.i = i; } public static Test1 operator +(Test1 a,Test1 b) { Test1 result = new Test1(a.Real+b.Real,a.i+b.i); return result; } }
همانگونه که مشاهده میکنید دو فیلد برا قسمت اعشار و صحیح عدد ایجاد کرده ایم و یک سازنده ساده نیز قرار داده ایم حال برای ایجاد override مربوط به عملگر ابتدا سطح دسترسی سپس عبارت static چون این نمونه override حتما باید بصورت static باشد سپس عبارت operator و سپس نوع عملگری که میخواهیم مشخص کنیم که در این مثال عملگر جمع میباشد و درون پرانتر هم دو پارامتری که میخواهیم با هم جمع کنیم که هردو نیز از نوع کلاس جاری میباشند سپس درون بدنه نیز یک شی جدید از نوع کلاس جاری ایجاد میکینم و درون پرانتز عملیاتی که میخواهیم انجام شود را قرار میدهیم که در این مثال این عملیات این است که قسمت صحیح دو عدد باهم و قسمت اعضار دو عدد نیز با هم جمع شوند و در انتها نیز نتیجه را به خروجی ارسال میکند.
حال میتوان درون main برنامه برای دیدن نتیجه بدین صورت نوشت
static void Main(string[] args) { Test1 o = new Test1(20, 5); Test1 c = new Test1(12, 2); Test1 result = o + c; Console.WriteLine(result.Real + " " + result.i); Console.ReadKey(); }
همانگونه که مشخص است دو شی با مقادیر مختلف ایجاد کرده ایم سپس نتیجه را درون شیی دیگر از نوع کلاس مورد نظر قرار میدهیم.