5- اگه کد زیر بنویسم رشته C++ همچنان در حافظه هیپ وجود داره؟ چون string کلاسه اینو پرسیدم.
کد:
string string1 = "C++";
string1 = "C#";
اولا Heap ای وجود نداره، شما در هیچ جای کد #C تون به ساختار حافظه دسترسی ندارید که بگید نوعش Heap هست یا نیست. مثل اینه که شما در اتاقی باشید که و در مورد رنگ لوازم خانه واحد بالایی نظر بدید.
ثانیا از لحظه ای که شما اون مقدار دهی دوم رو انجام دادید، شیء مربوط به "++C" در اختیار GC که مدیریت حافظه های داخل NET. رو بر عهده داره قرار میگیره که هر وقت لازم دونست آزادش کنه. از دید کد شما دیگه اون حافظه بلا استفاده و آزاد شده است، ولی از نظر فنی ممکنه به این زودی آزاد نشه و در حافظه سر جایش بمونه. این باقی موندنش مشکل ساز نیست، کد شما درگیر این قضیه نیست که کی آزاد بشه.
برای کد شما فرقی نمی کنه که کی آزاد میشه و به هر حال اصولا آزاد سازی با تاخیر صورت میگیره، کد شما هم کنترلی روی اون زمان آزاد سازی نداره.
6- به عکس زیر نگاه کنید اون علامت هایی که زدم درسته؟ (به عددها توجه نکنید برای راهنمایی گذاشته شده منظورم خود کروشه است)
شما وقتی متغیری رو از نوع آرایه فلان تعریف کردید، طبعا موقع مقدار دهی با new هم همون نوع آرایه رو می نویسید، تا اینجای کار اشتباه نیست، اما شما نمی توانید برای یک ارایه دندانه دار چیزی مثل int[2][2] رو تعریف کنید، این آرایه دو بعدی نیست که شما دو سطر و دو ستون داشته باشید. شما باید یک []int[2] ای بسازید که بعد اعضاء اش حالا می توانند int[2] باشند یا نباشند. نمی توانید در تعریف بجز اون بعد اول (اندیس اول) بقیه رو مقدار دهی کنید. همانطور که می توانید [][][2]new int رو تعریف کنید، ولی [][4][2]new int رو نه.
7- دو تا سوال از گذشته: آیا جمله های زیر درست هستند
الف: یک dll یا 32 بیتیه یا 64 بیتی و نمی شه همزمان هم 32 بیتی باشه و هم 64 بیتی
چیزی که میگید برای کتابخانه هایی که برای اجرا توسط ماشین مجازی ساخته شدن میتونه نادرست باشه، چون ماشین مجازی این امکان رو میده که کد خروجی موقع اجرا تغییر شکل بده.
فرضا NET. ماشین مجازی داره، dll ای که در محیط NET. میسازید، مستقیم در پردازنده کامپیوتر تون اجرا نمیشه و اصلا کدش به زبان پردازنده نیست. برای همین کتابخانه ای که با #C یا Visual Basic .NET کد نویسی می کنید میتونه با یک تنظیم طوری کامپایل بشه که در محیط 32 بیتی به کد ماشین 32 بیتی ترجمه بشه و در محیط 64 بیتی به کد ماشین 64 بیتی و همزمان هر دوشون رو پشتیبانی کنه. اما در مورد کتابخانه هایی که به زبان ماشین پردازنده کامپایل می کنند و به اصطلاح Native هستند، مثلا کامپایلر های C++ Native (برخلاف C++ CLI) حرفتون درسته. دقت کنید که ماشین مجازی داشتن الزاما به این معنی نیست که حتما همزمان بتونه 32 / 64 بیتی باشه. فرضا ویژوال بیسیک 6 (ویژوال بیسیک کلاسیک) هم ماشین مجازی داره ولی خروجی اش همیشه 32 بیتی ئه.
ب: اگه anycpu رو انتخاب کنیم و در برنامه خودمون dll های 32 بیتی و 64 بیتی همزمان داشته باشیم اونایی که 32 بیتی هستن 32 بیتی اجرا میشن و اونایی که 64 بیت هستن 64 بیتی
نه، یک برنامه که داره الان در مدل حافظه 32 بیتی اجرا میشه نمیتونه با کتابخانه ای که برای مدل حافظه 64 بیتی نوشته شده ارتباط برقرار کنه و برعکس. همیشه باید با هم منطبق باشند.
اگر روی Any CPU قرارش دادید و برنامه تون در ویندوز 32 بیتی اجرا بشه، باید حتما با dll هایی کار کنید که یا 32 بیتی باشند یا همزمان 32/64 بیتی رو پشتیبانی کنند و هم برنامه و هم dll ها در مدل حافظه 32 بیتی اجرا خواهند شد.
اگر روی Any CPU قرارش دادید و برنامه تون در ویندوز 64 بیتی اجرا بشه، باید حتما با dll هایی کار کنید که یا 64 بیتی باشند یا همزمان 32/64 بیتی رو پشتیبانی کنند و هم برنامه و هم dll ها در مدل حافظه 64 بیتی اجرا خواهند شد.
8- بهترین متغیر برای نشان دادن کد اسکی یک کاراکتر چیه؟ منظورم اینه چون کد اسکی یک کاراکتر به عدد تبدیل می شه از short استفاده کنیم یا int
ابتدا این مورد رو در نظر بگیرید که جدول ASCII همون جدول 7 بیتی System.Text.Encoding.ASCII ئه که اصلا کاراکتر هایی مثل حروف زبان فارسی و عربی داخلش جا نمیشه. اگه منظورتون کد کاراکتر ها است، نباید از عبارت ASCII استفاده کنید. کد کاراکتری که شما عموما بهش رجوع میکنید یا Unicode ئه که 16 بیتی است و Encoding عادی ویندوز و NET. ئه و یا UTF-8 که بیشتر در وب و اینترنت کاربرد داره و طول کاراکتر هایش متغیره.
از دیدگاه های متفاوت نتیجه های متفاوتی میگیرید. در حالت کلی بهترینی وجود نداره.
اگر هدف کاهش حجم حافظه مورد نیاز باشه، UTF-8 که با byte کار میکنه بهتر از short یا int ئه.
اگر هدف افزایش سرعت باشه، int در حالت کلی سربار پردازشی کمتری داره چون بردازنده های مدرن فعلی معماری شون حالتی داره که محاسبات 32 بیتی براشون راحت تر از پردازش روی انواع داده ای کوچکتره.
9- در جای خالی زیر چه کلمه ای باید بذاریم:
.NETFramewrok ماشین مجازی ... است. ( .NET یا ویندوز)
هیچکدوم، NET Framework. ماشین مجازی نیست، Framework ئه، یک چارچوب ئه، یک مجموعه نرم افزاری است. داخل NET Framework یک بخشی وجود داره که ماشین مجازی اونه.
ماشین مجازی داخلش اسم مشخصی هم داره، اسمش Common Language Runtime ئه، یا همون CLR. خود NET Framework. معادل اون ماشین مجازی نیست، ماشین مجازی فقط یک جزء داخلشه.
10- من مفهوم struct که مخفف structure هست رو درک نمی کنم. یعنی مایکروسافت یک اسم بی معنی براش انتخاب کرده یا این نام گذاری هدفمنده. این ساختار بودن رو درک نمی کنم که داخل کلاس قرار می گیره.
داده های شما میتوانند ساده باشند مثل int یا ترکیبی از چند داده مختلف باشند که کنار هم معنی خاصی میدهند، مثل مشخصات پلاک خودرو. شما می توانید پلاک خودرو رو بصورت کلاس تعریف کنید، اما بخاطر ذات کلاس ها که reference type هستند گاهی این کلاس بودن دردسر میشه، مثلا زمانی که میخواهید از مقادیر داده ترکیبی تون کپی بگیرید و نمی خواهید با تغییر مقدار در یک کپی، اون یکی مقدار هم تغییر کنه.
struct دو تا ویژگی داره که مناسب داده های ترکیبی است. اولا value type ئه و تکثیر مقادیرش ساده است و ثانیا ترتیب و موقعیت قرارگیری داده هاش در حافظه مشخص و قابل تنظیمه که برای ارتباط با محیط خارج از NET. که مملو از اینجور ساختار ها است مناسبش می کنه. برخلاف کلاس که شما نه میدانید که مقادیر داخل شیء با چه ترتیبی در حافظه ذخیره شده اند و نه براتون اهمیتی پیدا میکنه.
11- توی یک انجمن دیگه یک فردی یک سوالی پرسید و یک برنامه نویس مفهوم کلاس رو به این صورت توصیف کرد:
"کلاس یک مفهوم انتزاعیه" ...
"فرض کنید که یه روز در اتاق تون نشسته اید و یک مفهوم میاد در ذهن تون. این مفهوم استوانه ای سفالی رو توصیف می کنه که یک قاعده ی اون بسته و قاعده ی دیگر اون باز هستش و برای اون یک دسته در وجه جانبی در نظر گرفته شده. کاربرد این مفهوم می تونه نوشیدن مایعات باشه. شما نام این مفهوم Class رو می ذاریدو لیوان (mug). قاعدتا لیوان توصیف شده تا الان یک مفهوم بوده و تا زمانی که یک شی فیزیکی (object) از اون ساخته نشه، نمیشه ازش برای آشامیدن مایعات استفاده کرد."
می خوام بدونم این تعریف درسته چون در ویژوال استودیو ما داخل کلاس انواع کد ها رو می بینیم یا متغیر ها رو و شاید فقط یک چیز در ذهن ما نباشه.
مثلا ما می تونیم کلاس وسائل نقلیه داشته باشیم که شامل سواری و اتوبوس و هواپیما می شه که مثلا برای کلاس سواری می تونیم سمند و پراید رو داشته باشیم. حالا کلاس وسائل نقلیه، سواری، اتوبوس و هواپیما یک مفهوم هستند اما سمند و پراید هر کدوم یک شی هستند. اما در عین شی بودن می تونن یک کلاس هم باشن چون دارای اجزای مختلفی هستند هم دارای خواص و هم متد هستند. و کلا این بحث کلاس و شی در هم تنیده شده هستن و بعضی وقت ها آدم گیج می شه. چون اکثرا دیدم که دو نوع برداشت از سی شارپ دارن. یک عده میگن هر چی ما در سی شارپ بنویسیم فقط به صورت شی گرایی هست و به غیر از شی گرایی نمی تونیم طور دیگه ای بنویسیم. حتی مقدار یک متغیر رو شی می دونن. اما من چند وقت پیش یک پروژه ای دیدم که نوشته بود من یک برنامه در سی شارپ نوشتم و مثلا انقدر پول می دم یکی به صورت شی گرایی درش بیاره. آیا واقعا همینطوری که ما کدها رو می نویسم داریم روش شی گرایی رو به کار می بریم یا اینکه شی گرایی دارای یک ساختار درست و منظم و حرفه ایه که باید طبق اصولی رعایت بشه. اگه اینطور هست این ساختار رو به صورت کلی و تیتر وار نام ببرید.
چند تا نکته است که البته با ترتیب متفاوتی نسبت به سوال شما مطرح می کنم.
اولا بعضی زبان ها ترکیبی از چند شیوه برنامه نویسی رو پشتیبانی می کنند، مثل ++C، به همین جهت ممکنه یک کد ++C با دید شیء گرایی نوشته شده باشه یا نوشته نشده نباشه که به اینجور زبان ها Multi Paradigm میگن. خیلی اوقات کدی به عنوان کد زبان ++C معرفی میشه که شیء گرا هم نیست در حالی که در اصل یک کد زبان C ئه، ولی چون ++C از توسعه C بدست اومده پشتیبانیش میکنه. #C جزو این زبان ها نیست و ذاتا شیء گرا است، بنابراین اگه کسی کدی به زبان #C نوشته، شیء گرایی در اون وجود داره، حالا ممکنه کد نویس خیلی از کلاس و شیء استفاده نکرده باشه و تاکیدش روی متد ها باشه، ولی به هر حال دیدگاه شیء گرایی در همه کد های #C هست.
ثانیا کلا هر چیزی که بصورت نرم افزاری بوجود اومده یک مفهوم انتزاعی است، بوجود اومده تا شما بتوانید با پردازنده کامپیوتر ارتباط برقرار کنید، ازش کار بکشید و خروجی ای دریافت کنید که برای شما قابل فهم باشه.
وگرنه پردازنده کامپیوتری که فقط بیت های 0 و 1 رو میشناسه هیچ درکی از کلاس، متد، متغیر، ویژوال استدیو، ویندوز، فایل، فولدر و ... نداره.
تمامی این موارد که برای شما معنی داره برای پردازنده کامپیوتر بی معنیه. همانطور که درکی که پردازنده از بیت ها داره برای شما خیلی سطحی و فاقد هوشمندی است.
ثالثا اصول برنامه نویسی به دلایل فنی یا برای راحت تر شدن کار بوجود میان، نه برای ایجاد کردن محدودیت های غیر منطقی. اگر در فلان زبان فرضا روی اصول شیء گرایی تاکید میشه به این دلیل ئه که کامپایلر زبان یا خارج از یکسری قواعد نمیتونه کد رو کامپایل کنه، یا طوری طراحی شده که اگه یکسری قواعد و اصول رعایت بشه بتونه کد خروجی رو بهتر بهینه کنه. وگرنه برای طراح کامپایلر چه اهمیتی داره که شما که در خونه تون در حال کد نویسی هستید کد رو اصولی می نویسید یا نه. مادامی که شما نتیجه ای که لازمه از شیوه کد نویسی تون میگیرید اهمیتی نداره که چقدر با اصول پیش میرید.