یک ویژگی عضوی است که ابزاری انعطاف پذیر را برای خواندن و نوشتن مقدار یک فیلد private فراهم می کند. ما از ویژگی ها به عنوان عضوهای داده های public استفاده میکنیم، اما در واقع، آنها متدهای ویژه ای هستند که accessor ها نامیده میشوند.
در این مقاله، ما بیشتر در مورد ویژگی ها و نحوه استفاده از آنها در #c استفاده میکنیم.
این مقاله، سرفصلی از دوره آموزشی زیر میباشد:
- کلاسها و سازنده ها
- ویژگیها
- constant ،Static member ها و Extension Method ها
- Anonymous Type ها و Nullabel Type ها
- ساختارها
- شمارنده ها
- وراثت
- Interface ها
- کلاسهای Abstract
- Generic ها
- Queue, Stack, Hashtable
- Generic List و Dictionary
- Delegate ها
اگر می خواهید محتویات کامل این دوره را ببینید ، می توانید بر روی لینک سطح متوسطه #C کلیک کنید.
برای دانلود سورس این مقاله، میتوانید بر رو لینک سورس ویژگیها در #c کلیک کنید.
ما قصد داریم این مقاله را به بخشهای زیر تقسیم کنیم:
- سینتکس ویژگی
- خصوصیات فقط خواندنی و فقط نوشتنی
- قابلیت دسترس پذیری ویژگی
- ویژگیهای پیاده سازی خودکار
- نتیجه گیری
سینتکس ویژگی
سینتکس تعریف یک ویژگی به صورت زیر مورد استفاده قرار میگیرد:
1 2 3 4 5 6 7 8 9 10 11 |
Access_Modifier Type PropertyName { get { //read actions } set { //write action } } |
همانطور که میبینیم، یک ویژگی میتواند شامل دو بلاک کد باشد. بلاک get شامل دستوراتی است که زمانیکه ما یک ویژگی را میخوانیم اجرا میشوند. بلاک set شامل دستوراتی است که زمانیکه درون یک ویژگی مینویسیم اجرا میشود:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 |
public class Student { private string _name; private string _lastName; public string Name { get { return _name; } set { _name = value; } } public string LastName { get { return _lastName; } set { _lastName = value; } } public Student(string name, string lastName) { _name = name; _lastName = lastName; } public string GetFullName() { return _name + ' ' + _lastName; } } |
در مثال بالا، ما میبینیم که فیلدهای private ما از طریق ویژگی ها در اختیار ما قرار میگیرند. اگر ما بخواهیم مقدار فیلد name_ را بخوانیم، تمام کاری را که باید انجام دهیم صدا زدن ویژگی Name از آبجکت student میباشد. همین کار برای فیلد lastName_ نیز صورت میگیرد. علاوه بر این، اگر بخواهیم یک مقدار را درون فیلدها اختصاص دهیم، تمام کاری را که باید انجام دهیم فراخوانی بلاک set از ویژگیها میباشد:
1 2 3 4 5 6 7 8 9 10 11 12 13 |
class Program { static void Main(string[] args) { Student student = new Student("John", "Doe"); string name = student.Name; //call to a get block of the Name property string lastName = student.LastName; // call to a get block of the LastName property student.Name = "David"; //call to a set block of the Name property student.LastName = "Dauni"; // call to a set block of the LastName property } } |
ویژگی ها میتوانند کد پیچیده ای درون بلاکهای set یا get داشته باشند. آنها به خواندن و یا نوشتن فقط یک مقدار محدود نیستند. ما در آنها میتوانیم از شرطها و یا فراخوانی متدها و غیره استفاده کنیم. در بلاکهای get یا set:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
public int X { get { return _x; } set { _x = CheckValue(value); } } private int CheckValue(int val) { //code execution in here } |
ویژگیهای فقط خواندنی و فقط نوشتنی
ما میتوانیم یک ویژگی تعریف کنیم که فقط یک بلاک get دارد و بلاک set ندارد. این نوع از ویژگی، ویژگی فقط خواندنی نامیده میشود. اگر ما یک ویژگی فقط خواندنی ایجاد کنیم، آنگاه فقط میتوانیم مقدار آن فیلد private را بخوانیم. ایجاد ویژگیهای فقط خواندنی در داخل کلاس کاملاً کاری مرسوم است. کاری را که ما انجام میدهیم این است که مقدار را با متد سازنده کلاس ست میکنیم و سپس از مقدار آن در کل کلاس استفاده میکنیم. اما هرگز،مقدار آن را خارج از سازنده ست نمیکنیم. اگر این کار را انجام دهیم در نتیجه، کامپایلر یک خطا به ما نشان میدهد:
1 2 3 4 |
public string Name { get { return _name; } } |
به همین ترتیب، همانطور که ما میتوانیم یک ویژگی فقط خواندنی ایجاد کنیم، یک ویژگی فقط نوشتنی نیز میتوانیم ایجاد کنیم. این نوع از ویژگی، فقط بلاک از نوع set دارد و بلاک get ندارد. ایجاد ویژگیهای فقط نوشتنی، مورد مرسومی نیست. البته اگر ما به آن نیاز داشته باشیم، میتوانیم فقط مقادیر را با این نوع از ویژگی set کنیم و مقادیر را نخوانیم:
1 2 3 4 |
public string Name { set { _name = value; } } |
قابلیت دسترس پذیری ویژگی
اگر ما میخواهیم دسترسی به ویژگی را محدود کنیم میتوانیم یک (public, private…) access modifier برای آن تعیین کنیم. اما در #C ما حتی میتوانیم دسترسی به accessor های get یا set را override کنیم. بنابراین کاری که ما میتوانیم انجام میدهیم تعریف یک ویژگی public است که public get accessor و private set accessor دارد. اگر ویژگی ما، یک ویژگی public است نیازی نیست کلمه کلیدی public را برای get accessor اضافه کنیم، چرا که در هرصورت، آن خودش public خواهد بود:
1 2 3 4 5 |
public string Name { get { return _name; } private set { _name = value; } } |
این به این معنی است که ما میتوانیم ویژگی Name را در تمام کلاسها بخوانیم اما فقط داخل کلاس Student میتوانیم مقدار به داخل آن set کنیم.
زمانیکه ما از یک accessor overriding داخل یک ویژگی استفاده میکنیم، باید به قوانین زیر توجه کنیم:
- ما میتوانیم سطح دسترسی فقط یک accessor را تغییر دهیم. اصلاح در هر دو accessor هیچ دلیل منطقی ندارد. اگر بخواهیم هر دو accessor را تغییر دهیم، تنها باید سطح دسترسی خود ویژگی را تغییر دهیم.
- ما نمی توانیم از access modifier در بلاک های get یا set که دارای محدودیت در access modifier اعمال شده روی خود ویژگی هستند استفاده کنیم. بنابرین، اگر ویژگی ما private است، آنگاه داشتن بلاک get یا set از نوع public هیچ توجیه منطقی ندارد.
ویژگیهای پیاده سازی خودکار
اگر هیچ logic اضافی در accessor ویژگی نیاز نیست، آنگاه میتوانیم از ویژگیهای پیاده سازی خودکار برای نحوه خوانایی بیشتر و مختصرتر در تعریف ویژگی ها استفاده کنیم. این ویژگی پیاده سازی خودکار فقط شامل کلمات کلیدی get و set میباشد نه هیچ چیز دیگر:
1 2 |
public string Name { get; set; } public string LastName { get; set; } |
وقتیکه ما همچین ویژگیهایی را تعریف میکنیم، کامپایلر یک فیلد private برای ما ایجاد میکند که فقط میتواند توسط accessor های get یا set آن ویژگی مورد دسترسی قرار بگیرد.
بنابراین در مثال ما، بجای:
1 2 3 4 5 6 7 |
private string _name; public string Name { get { return _name; } set { _name = value; } } |
فقط میتوانیم این را بنویسیم:
1 |
public string Name { get; set; } |
در ویژوال استودیو، ما حتی یک پیشنهاد برای استفاده از این ویژگی خودکار دریافت میکنیم:
نتیجه گیری
عالی.
در این مقاله ما یاد گرفتیم:
- در مورد ویژگیها و سینتکس آن
- نحوه استفاده از ویژگیهای فقط خواندنی و فقط نوشتنی
- نحوه تغییر سطح دسترسی ویژگی
- راه استفاده از ویژگیهای پیاده سازی خودکار
در مقاله بعدی، ما در مورد متدهای static، کلاسهای static و extension method ها صحبت میکنیم.