PDA

View Full Version : سوال: ثبت مشخصات یک فرم در فرم دیگر



ahnsolution
دوشنبه 21 مرداد 1387, 17:57 عصر
سلام
لطفا راهنمائی بکنین که مشکل در کجاست وقتی اجرا میکنم

از خود فرم دوبار میسازه

form1 FrmNew = new form1();

FrmNew.lbl_family.Text = nam.Text;
FrmNew.operatorid.Text = codekarbari.Text;
FrmNew.Show();

ممنونم

Moslemu
دوشنبه 21 مرداد 1387, 17:59 عصر
سلام. مشکل از اینجاست که شما وقتی فرمی رو با New می سازید یه فرم جدیده و وقتی که اونو Show می کنید همون فرم جدید نشون داده می شه.

ahnsolution
دوشنبه 21 مرداد 1387, 18:04 عصر
سلام. مشکل از اینجاست که شما وقتی فرمی رو با New می سازید یه فرم جدیده و وقتی که اونو Show می کنید همون فرم جدید نشون داده می شه.



ممنونم ولی در فرم 2 من فرم 1 را نیو کردم.

Moslemu
دوشنبه 21 مرداد 1387, 18:08 عصر
از هر جایی که New کنید، یه نمونه ی جدید ازش می سازه!

ahnsolution
دوشنبه 21 مرداد 1387, 18:14 عصر
از هر جایی که New کنید، یه نمونه ی جدید ازش می سازه!


لطفا راهنمایی کنید چکار کنم؟

یه فرم لاگ این هست پس لاگ این کردن فرم اصلی رو میاره
من از فرم اصلی تو فرم لاگ این یکی نیو کرد.

لطفا با کد نشون بدین چکار کنم؟


مرسی

Moslemu
دوشنبه 21 مرداد 1387, 18:26 عصر
یه فرم لاگ این هست پس لاگ این کردن فرم اصلی رو میاره
من از فرم اصلی تو فرم لاگ این یکی نیو کرد...

این یعنی چی؟؟؟؟
اصلاً متوجه نشدم!!!!!!!!!!!!!!!!!:متفکر:

Mahdi.Kiani
سه شنبه 22 مرداد 1387, 09:26 صبح
به این لینک (http://barnamenevis.org/forum/showpost.php?p=571078&postcount=102) مراجعه کن.


سلام
همین چند روز پیش در مورد این نوع دسترسی ها صحبت شد. و غلط بودن تغییر modifire کنترل ها برای ای این منظور (روشی که شما استفاده کردید) بار ها گفته شده...
***

روش درست انتقال داده ، چیزی شبیه به .. این نمونه برنامه (http://barnamenevis.org/forum/showpost.php?p=574118&postcount=103) می باشد..
موفق باشید

hdv212
سه شنبه 22 مرداد 1387, 14:36 عصر
r.kiani جان ممکنه Documentهای این موضوع رو ارائه کنید تا ما هم یه چیزی یاد بگیریم ؟

Mahdi.Kiani
سه شنبه 22 مرداد 1387, 17:24 عصر
r.kiani جان ممکنه Documentهای این موضوع رو ارائه کنید تا ما هم یه چیزی یاد بگیریم ؟

کدوم موضوع؟

hdv212
سه شنبه 22 مرداد 1387, 17:52 عصر
سلام
همین چند روز پیش در مورد این نوع دسترسی ها صحبت شد. و غلط بودن تغییر modifire کنترل ها برای ای این منظور (روشی که شما استفاده کردید) بار ها گفته شده...
بر اساس کدام مستندات دسترسی به اعضای یک کلاس از طریق یک کلاس دیگه درست نیست ؟

اگر منظور شما Encapsulation بوده، خب درسته، حق با شماست، ولی به غیر از این، نیازمند مستنداتش هستم.
با تشکر

اَرژنگ
سه شنبه 22 مرداد 1387, 18:56 عصر
بر اساس کدام مستندات دسترسی به اعضای یک کلاس از طریق یک کلاس دیگه درست نیست ؟

اگر منظور شما Encapsulation بوده، خب درسته، حق با شماست، ولی به غیر از این، نیازمند مستنداتش هستم.
با تشکر

یکی از اصول شئ‌گرائی این است که همینطوری یک شیئ به عضوهای یک کلاس دیگر دستنمیاندازه و دستکاریشان کند.
اشیاء با همدیگر پیغام مبادله میکنند و از یکدیگردرخواست میکنند. به این طریق به شکل صریح اینکه یک ابجکت (کلاس) چه کارهایی بایدانجام بده مشخص هست و اگر تغییری قرار هست که انجام بشود فقط در یکجا (در داخل همانمتد کلاس و صریح) انجام میگیرد.
در حالت دیگر اشیاء تبدیل میشوند به یکسری متغییرهای سراسری، و اگر کاربردبخواهد عوض بشود باید تک تک هر جایی که از اون شیئ به شکل ضمنی استفاده شده تغییرات داده بشود.
حالا اینهایی که گفتم معلوم است که وجود داشتنشان به برنامه یک شکل سامانی میدهند .ولی بازهم من دنبال یک رفرانس میگردم.
مشکل اینکه فقط بگیم Encapsulationاست و بحث را منتفی کنیم اینه که در کتابهایک پاراگراف در مورد Encapsulationمینویسند و اصلش را میگند ولی دیر در مورد اینکه چه نوع کدی میشکنتش و یا پایدارش میکند توضیحی نمیدند، مثال همین بحث که ممکن است بر اساس Encapsulation باشد و یا نباشد. شاید یک سری اصولی دیگری هم هستند.
ولی غریضه میگه که این کار اشتباه است، یک سری دلایلش را هم که به فکرم میرسید نوشتم ولی بازهم به نظر خودم توضیح کامل ندادم.
۲تا موضوع دیگر هم که به غریضه میدانمکه درست نیستند ، ۱. استفاده از اعضا استاتیک برایه ارتباط بین ۲ فرم و ۲.استفادهاز یک کلاس استاتیک که مقادیر را درش نگهداری میکنند (اگر استنباطی بودن به اینکهدر یک کتاب درج شده باشد، یکی یک اسکن از یک کتاب فرستاد که همین روش اشتباه را یادمیداد اونهم در یک کتاب برایه یاد دادن برنامه نویسی در سی‌شارپ!) .

من میگم که همینطوی نمیتوانیم یک روش را بگیم که اشتباه است به دلیل اینکه با یک اصلی جوردرنمیاد، خوب به فرض هم بگیم که Encapsulation را میشکنه، اینکه هنوز یک عده‌ای میخواهند ازش استفاده کنند دلیلش چیه؟ در ظاهر در کوتاه مدت مشکل را فوری حل میکنه،با کد کمتر کار را انجام میده و میشه قضیه را تمام شده تلقی کرد. ولی اینکهEncapsulation را میشکند معنیش این است که در دراز مدت اشکالات دیگری پیش میاره، ازاشیاء به شکل مبهم استفاده میشه (یک سوال ، اینکه از اشیاء به شکل مبهم استفاده بشه چه اشکالی دارد؟ در برنامه نویسی صریح بودن و بیان کردن دقیق اینکه کد چه کاریانجام میده و فقط در یکجا جمع است و هر تغییراتی فقط در یکجا باید در یکجا اعمالبشه نگهداری از کد را ساده میکند (چرا ساده میکند؟ من نمیدونم، شاید هم میدونستم ولی بعد از سالها چیزهایی که به عنوان اصل یاد میگیریم و دلیلشان را میدانیم به غریزه تبدیل میشند و دیگر بهشان فکر نکرده انجام میدیم ).

برنامه نویسی فقط یک دانش نیست، هنر هم هستش، همانطوری که نمیشه یک نقاشی را فقط با پایبند بودن به اصول هنری کشید، همانطوری هم نمیشه فقط گفت یک کاری یک اصولی را میشکند و نباید ازشان استفاده کرد. بعضی وقتها شکستن اصول نیاز است، ولی داشتن بالانس که برنامه تبدیل به یک چیزه هشلهفت نشه، قابلیت دیدی میخواهد که معمولا در اختیار تازه کارها نیست، درضمن خیلی از برنامه‌ها با پایبند بودن به اصول بازهم بعد از یک مدتی به یک کابوستبدیل میشند، دیگر چه برسه به برنامه‌هایی که با شلی و یا بدون دیسیپلین نوشته شدند و اینکه برنامه نویس پیش خودش گفته بوده که بعدا درستش میکند (بعدا هیچ وقت نمیاد، اگر کاری را خراب شروع کنند همانطوری هم پیش میره).

به هر حال این برداشت من از این موضوع است، من دلم میخواد ایرادهای این نظر را بخوانم ، به نظرات دیگر چه موافق و چه مخالف و چه اصلا از یک بعد دیگر هم یک نگاهی بندازم. هر کی هرفکری به نظرش میاد بگد (اینکه یک طرز فکر درست و یا اشتباه است ربطی به درست و یااشتباه بودن نویسندش ندارد، نظرات از اشخاص جدا هستند و تنها اشتبهای که کسی میتواند انجام بده این است که افکارش را بازگو نکند که بداند که درست هستند و یانه، هم خودش را و هم دیگران را از دریافت حقیقتی که در ذهنش هست محروم میکند و ازپیشرفت خودش باز میماند، هر چی که چیزی که در فکرتان است اشتباهتر باشد، وقتی که درستش را یاد میگرید بیشتر سود میبرید، کسانیکه درستش را میدانند کمتر سود میبرند ویا اصلا هیچ‌سودی نمیبرند).

با تشکر از Linux

Mahdi.Kiani
سه شنبه 22 مرداد 1387, 19:05 عصر
اگر در فرم 2 ( در مثالی که شمات فرستادید) و به جای کد



f1.label1.Text = "Changed via Form2";


کد



f1.label1.Dispose();



نوشته شود چه اتفاقی می افد؟


قرض کنید یک class library نوشتید که قراره دیگران از این لایبرری شما استفاده کنند. ئ کلاسی مانند زیر در کلاس های شما می باشد:



class Adult
{
public uint age;

// other members
}



همه می دانید که برای Adult مقدار مینیمم سن باید 18 باشد.
آیا شما با کد فوق می توانید مطمئن شوید که class consumer شما مقدار age را به درستی وارد می کند؟
مگر اینکه در مستندات لایبرری خودتون تاکید کنید که "کاربر گرامی لطفا مقدار سن را در کلاس adult کمتر از 18 وارد ننمایید در غیر این صورت مسئولیت عواقب آن با خودتان می باشد!!!"

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



class Adult
{
private uint age=18;

public uint Age
{
get
{
return age;
}
set
{
if (value < 18)
throw new ArgumentOutOfRangeException();
age = value;
}
}

}



باز فرض کنید که شخصی به شما چیزی برای خوردن می دهد :
شما دو راه دارید
1) یا اینکه چشماتون را می بندید و دهنتون را باز می کنید که دوستتون هر چی خواست بریزه توی دهان شما ( که در این صورت معلوم نیست که پس از خوردن آن شی چه بلایی سر شما خواهد آمد. زنده خواهید ماند؟ به فضا خواهید رفت و ...)
2) هر چیزی که قراره به شا داده بشه که بخورید را ، از دئستتون می گیرید و پس از بررسی چند تا کار می توانید انجام دهید :
الف) آن چیز را می خورید ( دیتا درست است)
ب) آن چیز را به دوستتون بر می گردونید(دیتا خطرناکه)
ج) آن را اصلاح می کنید ( دیتا را ویرایش کرده و سپس می خورید)
...

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

و نکته آخر اینکه :
یکی از اصول مهم شی گرایی میگه که ،به هر کسی به همان اندازه که نیاز دارد اطلاعات بدهید، نه بیشتر نه کمتر)
وقتی فقط قراره text یک textbox از جای دیگری تغذیه شود، معنایی ندارد که backColor آن هم قابل دسترسی باشد..

Mahdi.Kiani
چهارشنبه 23 مرداد 1387, 09:35 صبح
در پست قبل، اشاره ای به معایب تغییر دادن (نا به جای) Modifier ها ، توضیحاتی دادم.
در این پست در نمونه برنامه ای که در پست شماره 7 (http://barnamenevis.org/forum/showpost.php?p=572129&postcount=7) فرستاده بودم خواهم داد تا مطلب برای دوستانی که آشنایی کمتری با این روش دارند، مفید واقع شود.

در مورد روشی که استفاده شده، روش استانداری است که خود کلاس های دات نت نیز از آن استفاده می کند..
در این روش شما از شی که میخواهید ازآن استفاده کنید، یک آبجکت ایجاد کرده، و سپس، متد هایی برای هندل کردن رویداد (event) های آن بر حسب رویداد های موجود می نویسید.
این عمل شما را از دسترسی مستقیم به اعضای یک شی که می تواند بسیار خطر ناک باشد، بی نیاز می کند.
متاسفانه مشکل بسیاری از برنامه نویسان، آشنتا نبودن به delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) ها، و event ها که بر پایه delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) ها کار می کنند، می باشد.
به این صورت که اکثرا فکر می کنند، که تنها از رویداد های موجود و تعریف شده می توان استفاده کرد و یا تا به حال اقدامی برای ایجاد رویداد های سفارشی برای کلاس های خودشان نکرده اند.
نحوه تعریف یک رویداد به صورت زیر می باشد:
ابتدا نیاز به یک delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) خواهید داشت:





public delegate void DataChangedEventHandler(object sender, dataChangedEventArgs e);





استانداری که در تعریف delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) ها برای پیاده سازی رویداد ها، در دات نت مشخص شده، اینه که آرگومان های ورودی Delegate ای که برای پیاده سازی رویدادی به کار می رود، شامل یک متغیر از نوع object و یک متغیر از نوع کلاس EventArgs (http://msdn.microsoft.com/en-us/library/system.eventargs.aspx)می باشد. شما می توانید از این استاندارد رعایت نکنید، ولی این موضوع به دلایلی تایید نمی شود.
آرگومان اول نشان دهنده آبجکتی است که رویداد مورد نظر نظر را raise (http://msdn.microsoft.com/en-us/library/wkzf914z.aspx)خواهد کرد. این عمل را با پاس کردن کلمه this که اشاره گر کلاس فعلی است، به متدی که رویداد را هندل می کند، نشان می دهیم.
اما در delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) فوق ،آرگومان دوم، کلاسی است به نام DataChangedEventArgs که خود از کلاس EventArgs (http://msdn.microsoft.com/en-us/library/system.eventargs.aspx)ارث بری می کنه.. و در عمل تضادی وجود ندارد، چون عمل UpCasting صورت خواهد گرفت.
تعریف کلاس DataChangedEventArgs به صورت زیر می باشد:






public class DataChangedEventArgs : EventArgs
{
public dataChangedEventArgs(String data)
{
newData = data;
}
private String newData;

public String NewData
{
get { return newData; }

}

}





حال پس از تعریف delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) ، می توانید رویداد خود را بر اساس آن تعریف نمایید.





public event DataChangedEventHandler DataChanged;





حال شما رویداد کاملا جدیدی تعریف کردید. که میتوانید درون هر کلاسی آن را قرار دهید. حتی فرم.(چون فرم نیز به خودی خود کلاسی بیش نیست...)
در مثالی که در پست قبل فرستاده شد، فرم 2 علاوه بر رویداد های تعریف شده از قبل، دارای رویداد جدیدی که من آن را DataChanged نامیدم، می باشد.

علاوه بر این من در کلاس فرم2، متدی به شکل زیر تعریف کردم، که مسئول raise (http://msdn.microsoft.com/en-us/library/wkzf914z.aspx)کردن رویداد مذکور می باشد:





protected virtual void OnDataChanged(dataChangedEventArgs e)
{
if (DataChanged != null)
this.DataChanged(this, e);
}





دقت کنید، که برا raise (http://msdn.microsoft.com/en-us/library/wkzf914z.aspx)شدن رویداد مورد نظر نیاز به دو آرگومان دارید از نوع آرگومان هایی که در delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) شما تعریف شده است. اما چون raise (http://msdn.microsoft.com/en-us/library/wkzf914z.aspx)شدن این رویداد، در همان کلاسی است که رویداد تعریف شده، در متد OnDataChanged فقط آرگومانی از نوع دومین آرگومان delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) وجود دارد. چون آرگومان اول همان this می باشد..
توجه کنید که قبل از raise (http://msdn.microsoft.com/en-us/library/wkzf914z.aspx)کردن رویداد، حتما از null نبودن آن اطمینان حاصل کنید، چون در این صورت exception ای با متن خطای "Object reference not set to an instance of an object" در یافت خواهید کرد.

دقت کنید که برای raise (http://msdn.microsoft.com/en-us/library/wkzf914z.aspx)کردن، رویداد خود، نیازی به نوشتن متد مجزایی مانند، OnDataChanged ندارید، اما اگر کلاس شما قابل ارث بری باشد، و این رویداد بتواند، در کلاس های فرزند، override شود، آن موقع به همچین متدی نیاز خواهید داشت، به همین دلیل است که من آن را Protected و Virtual تعریف کردم.
زمان فراخوانی این متد زمانی است که باید رویداد شما raise (http://msdn.microsoft.com/en-us/library/wkzf914z.aspx)شود. مثلا درون textbox ای که درون فرم2 می باشد، داده خود را وارد کرده و می خواهید با کلیک کردن دکمه ای این داده به متدی که delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) شما به آن ارجاعی دارد و رویداد شما آن را فراخوانی خواهد کرد، فرستاده شود.
نحوه فراخو.انی هم به این شکل می باشد:




if (!String.IsNullOrEmpty(textBox1.Text.Trim()))
OnDataChanged(new dataChangedEventArgs(textBox1.Text));





حال برای استفاده از این رویداد، مانند رویداد های دیگر باید کدی شبیه به کد زیر بنویسید:
فرض کنید که رویداد فوق در فرم2 تعریف شده و شما می خواهید ازآن در فرم1 استفاده کنید:





Form2 form2 = new Form2();
form2.DataChanged += new Form2.DataChangedEventHandler(form2_DataChanged);
form2.Show();




form2_Datachanged نام متدی است که delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) مذکور به آن اشاره می کند:



void form2_DataChanged(object sender, Form2.dataChangedEventArgs e)
{
this.textBox1.Text = e.NewData;
}





همانطور که مشاهده می کنید، آرگومان های این متد نیز، شبییه آرگومان های delegate (http://msdn.microsoft.com/en-us/library/900fyy8e(VS.71).aspx) تعریف شده می باشد ( در واقع امضای آن ها یکی است که این از قوانین تعریف delegate ها می باشد)

حال توسط e که از جنس DataChangedEventArgs می باشد، به پروپرتی NewData که حاوی مقدار جدید در فرم2 می باشد، دسترسی خواهید داشت.

دقت کنید که همه چیز در مثال فوق شبیه استاندارد های خود دات نت می باشد. و نکته مهمتر این است که در این روش، شما، داده را از فرم2 در یافت می کنید که می توانید بر روی آن نظارت کامل داشته باشید نه اینکه فرم2 داده را به کنترل های شما تزریق کند.(بین این دو تفاوت بزرگی می باشد که همه مشکلات، ناشی از درک نکردن این موضوع است.).. و نکته سوم این که در این روش خاصیت modifier مربوط به textBox1 همان private می باشد وتغییری در آن داده نشده است.

پ و :
چون مطالب را همین الان وبا عجله نوشتتم ممکن است غلط املایی زیادی در آن مشاهده کنید.

linux
چهارشنبه 23 مرداد 1387, 21:03 عصر
یکی از اصول شئیگرائی این است که همینطوری یک شیئ به اعضایه یک کلاس دیگر دست نمیاندازه و دستکاریشان کند.
اشیاء به همدیگر مساج رد و بدل میکنند و از یکدیگر درخواست میکنند. به این طریق به شکل صریح اینکه یک ابجکت (کلاس) چه کارهایی باید انجام بده مشخص هست و اگر تغییری قراره به که انجام بشد فقط در یکجا (در داخل همان متد کلاس و صریح) انجام میگیرد.
در حالت دیگر اشیاء تبدیل میشند به یکسری متغییر سراسری که یک به جز نگه داشتن یک سری متغییرات کاربرد دیگری ندارند، و اگر کاربرد بخواد عوض بشد باید تک تک هر جایی که از اون شیئ به شکل ضمنی استفاده شده تغییرات داده بشد.
حالا اینهایی که گفتم معلوم است که وجود داشتنان به برنامه یک شکل سامانی میدند و بر حس عام مشخص هستند. ولی بازهم من دنبال یک رفرانس میگردم.
مشکل اینکه فقط بگیم Encapsulationاست و بحث را منتفی اینه که در کتابها یک پاراگراف در مورد Encapsulationمینویسند و اصلش را میگند ولی دیر در مورد اینکه چه نوع کدی میشکنتش و یا پایدارش میکند توضیحی نمیدند، مثال همین بحث که ممکن است بر اساس Encapsulation باشد و یا نباشد. شاید یک سری اصولی دیگری هم هستند.
ولی غریضه میگه که این کار اشتباه است، یک سری دلایلش را هم که به فکرم میرسید نوشتم ولی بازهم به نظر خودم توضیح کامل ندادم.
۲ تا موضوع دیگر هم که غریضتا میدانم که درست نیستند ، ۱. استفاده از اعضا استاتیک برایه ارتباط بین ۲ فرم و ۲.استفاده از یک کلاس استاتیک که مقادیر را درش نگهداری میکنند (اگر استنباطی بودن به اینکه در یک کتاب درج شده باشد، یکی یک اسکن از یک کتاب فرستاد که همین روش اشتباه را یاد میداد اونهم در یک کتاب برایه یاد دادن برنامه نویسی در سی‌شارپ!) .

من میگم که همینطی نمیتوانیم یک روش را بگیم که اشتباه است به دلیل اینکه با یک اصلی جور درنمیاد، خوب به فرض هم بگیم که Encapsulation را میشکنه، اینکه هنوز یک عده‌ای میخواهند ازش استفاده کنند دلیلش چیه؟ در ظاهر در کوتاه مدت مشکل را فوری حل میکنه، با کد کمتر کار را انجام میده و میشه قضیه را تمام شده تلقی کرد. ولی اینکه Encapsulation را میشکند معنیش این است که در دراز مدت اشکالات دیگری پیش میاره، از اشیاء به شکل مبهم استفاده میشه (یک سوال ، اینکه از اشیاء به شکل مبهم استفاده بشه چه اشکالی دارد؟ در برنامه نویسی صریح بودن و بیان کردن دقیق اینکه کد چه کاری انجام میده و فقط در یکجا جمع است و هر تغییراتی فقط در یکجا باید در یکجا اعمال بشه نگهداری از کد را ساده میکند (چرا ساده میکند؟ من نمیدونم، شاید هم میدونستم ولی بعد از سالها چیزهایی که به عنوان اصل یاد میگیریم و دلیلشان را میدانیم به غریزه تبدیل میشند و دیگر بهشان فکر نکرده انجام میدیم ).

برانمه نویسی فقط یک دانش نیست، هنر هم هستش، همانطوری که نمیشه یک نقاشی را فقط با پایبند بودن به اصول هنری کشید، همانطوری هم نمیشه فقط گفت یک کاری یک اصولی را میشکند و نباید ازش استفاده کرد. بعضی وقتها شکستن اصول نیاز است، ولی داشتن بالانس که برنامه تبدیل به یک چیزه هشلهفت نشه، قابلیت دیدی میخواهد که معمولا در اختیار تازه کارها نیست، در ضمن خیلی از برنامه‌ها با پایبند بودن به اصول بازهم بعد از یک مدتی به یک کابوس تبدیل میشند، دیگر چه برسه به برنامه‌هایی که با شلی و یا بدانه دیسیپلین نوشته شدند و اینکه برنامه نویس پیشه خودش گفته بوده که بعدا درستش میکند (بعدا هیچ وقت نمیاد، اگر کاری را خراب شروع کنند همانطوری هم پیش میره).

به هر حال این برداشت من از این موضوع است، من دلم میخواد ایرادهایه این نظر را بخوانم ، به نظرات دیگر چه موافق و چه مخالف و چه اصلا از یک بعد دیگر هم یک نگاهی بندازم. هر کی هر فکری به نظرش میاد بگد (اینکه یک طرز فکر درست و یا اشتباه است ربطی به درست و یا اشتباه بودن نویسندش ندارد، نظرات از اشخاص جدا هستند و تنها اشتبهایه که کسی میتواند انجام بده این است که افکارش را بازگو نکند که بداند که درست هستند و یا نه، هم خودش را و هم دیگران را از دریافت حقیقتی که ذهنش هست محروم میکند و از پیشرفت خودش باز میماند، هر چی که چیزی که در فکرتان است اشتباهتر باشد، وقتی که درستش را یاد میگرید بیشتر سود میبرید، کسانیکه درستش را میدانند کمتر سود میبرند و یا اصلا هیچ‌سودی نمیبرند).
شی گرایی چیزی نیست که عجیب و غریب باشد، مفاهیم بسیار ساده و قابل فهم برای انسانها هست که می توانند انتزاع و تجرید کنند.

کلاس: یک تجرید و انتزاع هست ، حالا انتزاع یعنی چی!(abstraction)
دانش نامه رشد (http://daneshnameh.roshd.ir/mavara/mavara-index.php?page=%d8%a7%d9%86%d8%aa%d8%b2%d8%a7%d8%b 9&SSOReturnPage=Check&Rand=0)
"این عمل ذهنی از این قرار است که:
ذهن پس از آنکه چند چیز مشابه را درک کرد، آنها را با یکدیگر مقایسه می کند. اوصافی را که مخصوص به هر یک از آن هاست، کنارگذاشته و وجه تشابه و صفت مشترک میان همه آنها را بر می گزیند. سپس از آن صفت مشترک، یک مفهوم کلی می سازد که درباره همه آن افراد صادق است. در این هنگام گفته می شود که این مفهوم، از این چیز ها انتزاع شده و مفهومی انتزاعی است."
پس کلاس یک مفهوم انتزاعی هست
وقتی ما از کلاس انسانها حرف می زنیم یعنی خصوصیات مشترک همه انسانها را در ذهن مجسم می کنیم یعنی ما می توانید بدون در نظر گرفتن همه انسانها مفهومی در ذهن خودمان تجرید کنیم.
عضو یک کلاس یک موجود واقعی و قابل دسترس هست.
مثلا شما یک انسان هستید که داری مشخصات کاملا منحصر بفردی هستید که شما را از سایرین جدا می کند، پس در حقیقیت در یک کلاس دو موجود کاملا یکسان وجود ندارد، یا به عبارت دیگر هر گاه به دو عضو کلاس بر خورد کردیم که از همه لحاظ یکسان بودند یکی کپی آن دیگری هست.
هر عضو کلاس دارای خصوصیات و عملگردها و رخدادها هست که در آن کلاس موجود هست.

hdv212
پنج شنبه 24 مرداد 1387, 13:33 عصر
r.kiani جان ممنون از جواب کامل و بی نقصت
اما چیزی که خاطر نشان میکنم اینه که دستورالعمل برنامه نویسی کاملا بستگی به نوع و شرایط نرم افزار داره،
مشکلی که شما در نمونه برنامه ی این جانب مطرح کردید، نهایتا با ایجاد تابعی مثل زیر در هر فرم، بر طرف خواهد شد :

public string GetLabel1Text()
{
return this.label1.Text;
}

// or

public string GetLabel1Text
{
get
{
return this.label.Text;
}
}

و بدین معنی نیست که راه حل من اشتباه و راه شما تنها راه حله.
موفق باشید.

Mahdi.Kiani
پنج شنبه 24 مرداد 1387, 15:00 عصر
مشکلی که شما در نمونه برنامه ی این جانب مطرح کردید، نهایتا با ایجاد تابعی مثل زیر در هر فرم، بر طرف خواهد شد :

public string GetLabel1Text()
{
return this.label1.Text;
}

// or

public string GetLabel1Text
{
get
{
return this.label.Text;
}
}



عجیبه که شما چطور اون ایرادی که من در پست شماره 12 گفتم را نا دیده می گیرید. علاوه بر این ربط اون ایراد را به این کدی که نوشتید نمی فهمم..



اما چیزی که خاطر نشان میکنم اینه که دستورالعمل برنامه نویسی کاملا بستگی به نوع و شرایط نرم افزار داره،


یعنی اینکه، از یک فرمی بتوان، به راحتی کنترل های فرم دیگر را dispose کرد، باز هم بستگی به شرایط داره؟

اگر در فرم 2 ( در مثالی که شمات فرستادید) و به جای کد



f1.label1.Text = "Changed via Form2";


کد




f1.label1.Dispose();



نوشته شود چه اتفاقی می افد؟







و بدین معنی نیست که راه حل من اشتباه و راه شما تنها راه حله.


بدین معنی هست که روشی که شما بیان کردید غیر استاندارد و خلاف قوانین oop می باشد و لی روشی که من بیان کردم( که صد البته روش من نیست، روشی است که کلاس های داخلی خود دات نت نیز از آن پیروی می کنند)، استاندارد می باشد...

من حتی برای اینکه، مشکلات روشی که بیان کردید را بهتر برای شما روشن کنم، سناریویی را در همان پست 12 بیان کردم که فکر کنم گویای خیلی از مطالب بود...

یک سوال:
آیا تا بحال فکر کردید که چرا خاصیت modifier کنترل ها به صورت پیش فرض prtivate می باشند؟
قطعا به این معنا نیست که نباید در هیچ زمانی و تحت هیچ شرایطی نباید modifer را تغییر داد..
اما هر سخن جایی و هر نکته مکانی....
قطعا برای این عملی که شما می خواستید، انجام بدید ، ( یعنی تغذیه کردن مقدار text یک کنترل از طریق یک آبجکت دیگه)، تغییر دادن modifier مربوط به label اشتباه است.

hdv212
پنج شنبه 24 مرداد 1387, 16:13 عصر
یعنی اینکه، از یک فرمی بتوان، به راحتی کنترل های فرم دیگر را dispose کرد، باز هم بستگی به شرایط داره؟
r.kiani جان حالا کی خواسته فرم رو dispose کنه ؟ ما کی باشیم که بخواهیم فرم رو Dispose کنیم، اصلا در حد و اندازه های این حرفا نیستیم!


قطعا برای این عملی که شما می خواستید، انجام بدید ، ( یعنی تغذیه کردن مقدار text یک کنترل از طریق یک آبجکت دیگه)، تغییر دادن modifier مربوط به label اشتباه است.
گفتم که این مشکل رو میشه با استفاده از Propertiesها حل کرد (پست شماره 15)، در ضمن هرکسی ناخود آگاه از این شیوه در کد نویسیش استفاده میکنه، مگه تا حالا از این کد استفاده نکردید :

DataSet ds = new DataSet();
ds.Tables["myTable"] = this.dt;
چه زمانی شما خواستید از این کد استفاده کنید :

ds.Tables["myTable"].Dispose();


قطعا به این معنا نیست که نباید در هیچ زمانی و تحت هیچ شرایطی نباید modifer را تغییر داد..
میشه شما بگی هدف از تغییر Modifier یک کنترل چی میتونه باشه ؟

اَرژنگ
پنج شنبه 24 مرداد 1387, 17:15 عصر
دلیل استفاده از ابجکتها، تقسیم بندی منطقی برنامه است.
حالا اگر در یک قسمت اجازه عوض کردن مقادیر داخلی به هر ابجکت دیگری داده شده باشد، کنترل در اون قسمت ضعیف میشه، معلوم نیست که کدام ابجکت بر چه منطقی کیفی مقادیر یک ابجکت دیگر را عوض میکند.
استفاده از پروپرتی با باپلیک کردن مدیفیر یک عضو فرق دارد، یکیش به شکل علنی اعلام میکند که مقادیر در کجا عوض میشند و اگر کنترل بیشتر بر مقدار لازم باشد دقیقا در یکجا میشه منطق شرائط را نگه داشت.

Mahdi.Kiani
جمعه 25 مرداد 1387, 10:39 صبح
گفتم که این مشکل رو میشه با استفاده از Propertiesها حل کرد (پست شماره 15)، در ضمن هرکسی ناخود آگاه از این شیوه در کد نویسیش استفاده میکنه، مگه تا حالا از این کد استفاده نکردید :

DataSet ds = new DataSet();
ds.Tables["myTable"] = this.dt;
چه زمانی شما خواستید از این کد استفاده کنید :

ds.Tables["myTable"].Dispose();



سلام
شما به 2 تا نقش Class Creator و Class Consumer ، توجه ندارید..

Class Creator به شخصی می گویند، که کلاس یا اون شی خاص را طراحی می کند. طراحی اعم از اینکه ، آن شی چه خصوصیاتی دارد؟ چه رفتار هایی دارد؟ چه قسمت هایی از اون شی بایستی برای استفاده کننده های آن (Class Consumer) مشخص باشند، چه چیز هایی نباید مشخص باشند. مصرف کننده کلاس شما چه دسترسی هایی باید داشته باشید، چه دسترسی هایی نباید داشته باشد و بسیاری مطالب دیگر ...

Class Consumer هم به کسی می گویند که قرار است از کلاس شما استفاده کند..


در طراحی شی گرا، در هر لحظه شما باید، بدونید که در چه جایگاهی کد می نویسید، آیا Class Creator هستید؟ یا Class Consumer ؟ و یا هر دون آن ها؟ که غالبا اکثرا از نوع سوم هستند...

MyTable ای که شما در کد بالا نوشتید،ربطی به Class Creator ندارد. هر کسی به عنوان مصرف کننده کلاس Data Set می تواند جداولی را به آن اضافه کند، و هر عملی که بخواهد با آن ها انجام دهد..

این مثل این می ماند که من یک آبجکت از کلاس مثلا SqlConnection یا هر چیز دیگری بگیرم و پس از آنکه کارم با آن تمام شد، آن را Dispose کنم که عمل بسیار طبیعی است...

اما Dispose کردن، Lable ای که در فرم 1 شما می باشد( از طریق فرم 2) ، کاری نادرست است. به این دلیل که ، ممکن است شما در جایی دیگر از فرم1 نیاز به Label1 داشته باشید..

علاوه بر این Dispose فقط یک مثال بود از دسترسی که نباید داده می شد..

شما زمانی که فرم1 را طراحی می کنید، به عنوان Class Creator برای این فرم شناخته خواهید شد.
اینکه شما، دستور Dsipose را از فرم2 برای label1 از فرم1 نمی نویسید، و در واقع فقط خاصیت text آن را تغییر می دهید، به این دلیل است که شما در این مثال علاوه بر اینکه Class Creator برای فرم1 می باشد به عنوان Consumer آن نیز در فرم2 می باشید.

ولی اگر مصرف کننده فرم1 شما، شخصی غیر از خود شما باشد، آیا این تضمین باز هم وجود دارد که آن شخص هم به درستی از کلاس فرم1 و دسترسی هایی که به آن داید، استفاده کند؟

آیا این درست است که ادمین یک شبکه، پسورد administrator را در اختیار همه کاربران سایتش قرار دهد؟

همه روزه مشاهده می کنید تاپیک هایی با عنوان اینکه "چگونه به برنامه خود قابلیت مدیریت کردن کاربران با سطح دسترسی های متفاوت را بدهم؟" در همین تالار مشاهده می کنید..
این به چه دلیل می تواند باشد؟
اینکه آبدارچی شرکت تنها نیاز خواهد داشت که بدانید در انبار چه مقدار چایی دیگر موجود است ( شاید به همین هم نیاز نداشته باشید)
منشی شرکت دلیلی ندارد بداند که سود و زیاد شرکت در ماه گذشته، سال گذشته و ... چقدر بوده؟
آیا می توانید برنامتون را بدون قابلیت سطح دسترسی به کارفرما بدین و به کار فرما بگین که با یک چوب بالای سر کاربران نرم افزار شما بایستد و اجازه ندهد که کسی به قسمت های پی که نباید برود، دسترسی پیدا کند؟

پس باز هم به همین جمله ای خواهیم رسید که در یکی دو پست قبل بیان کردم:



یکی از اصول مهم شی گرایی میگه که ،به هر کسی به همان اندازه که نیاز دارد اطلاعات بدهید، نه بیشتر نه کمتر)
وقتی فقط قراره text یک textbox از جای دیگری تغذیه شود، معنایی ندارد که backColor آن هم قابل دسترسی باشد..

hdv212
جمعه 25 مرداد 1387, 12:52 عصر
سلام
شما به 2 تا نقش Class Creator و Class Consumer ، توجه ندارید..

Class Creator به شخصی می گویند، که کلاس یا اون شی خاص را طراحی می کند. طراحی اعم از اینکه ، آن شی چه خصوصیاتی دارد؟ چه رفتار هایی دارد؟ چه قسمت هایی از اون شی بایستی برای استفاده کننده های آن (Class Consumer) مشخص باشند، چه چیز هایی نباید مشخص باشند. مصرف کننده کلاس شما چه دسترسی هایی باید داشته باشید، چه دسترسی هایی نباید داشته باشد و بسیاری مطالب دیگر ...

Class Consumer هم به کسی می گویند که قرار است از کلاس شما استفاده کند..


در طراحی شی گرا، در هر لحظه شما باید، بدونید که در چه جایگاهی کد می نویسید، آیا Class Creator هستید؟ یا Class Consumer ؟ و یا هر دون آن ها؟ که غالبا اکثرا از نوع سوم هستند...
شما به من بگو آیا مایکروسافت که حکم ClassDesigner رو داشته برای برنامه نویسان، از این بابت نگرانی نداشته که DataSet.Tables رو در اختیار کاربران قرار بده ؟ چون ممکنه کسی myTable رو dispose کنه در حالی که توی همون فرم بهش نیاز داره!

نمیدونم چرا شما گیر دادی که کسی dispose نکنه، اگر کسی بخواد کنترلی رو در فرم دیگه dispose کنه، مشکل اینه که هنوز مسلط به برنامه نویسی نیست، باید بره برنامه نویسی رو یاد بگیره، و گرنه هیچ کس کلاسهای داخلی یک کلاس بیرونی رو dispose نمیکنه (این یکی از نکات اصلی برنامه نویسی OOP هست)


ولی اگر مصرف کننده فرم1 شما، شخصی غیر از خود شما باشد، آیا این تضمین باز هم وجود دارد که آن شخص هم به درستی از کلاس فرم1 و دسترسی هایی که به آن داید، استفاده کند؟

متاسفانه من 2-3 بار این موضوع رو جواب دادم، ولی شما باز تکرار میکنید، گفتم نگرانی شما در این زمینه با برگرداندن Modifier به همون حالت private و ایجاد یک Property و استفاده از اون پراپرتی در فرمهای دیگه حل میشه.


آیا این درست است که ادمین یک شبکه، پسورد administrator را در اختیار همه کاربران سایتش قرار دهد؟

همه روزه مشاهده می کنید تاپیک هایی با عنوان اینکه "چگونه به برنامه خود قابلیت مدیریت کردن کاربران با سطح دسترسی های متفاوت را بدهم؟" در همین تالار مشاهده می کنید..
این به چه دلیل می تواند باشد؟
اینکه آبدارچی شرکت تنها نیاز خواهد داشت که بدانید در انبار چه مقدار چایی دیگر موجود است ( شاید به همین هم نیاز نداشته باشید)
منشی شرکت دلیلی ندارد بداند که سود و زیاد شرکت در ماه گذشته، سال گذشته و ... چقدر بوده؟
آیا می توانید برنامتون را بدون قابلیت سطح دسترسی به کارفرما بدین و به کار فرما بگین که با یک چوب بالای سر کاربران نرم افزار شما بایستد و اجازه ندهد که کسی به قسمت های پی که نباید برود، دسترسی پیدا کند؟
شما دسترسی به خاصیت یک TextBox رو با به اشتراک گذاری پسورد یک سیستم مقایسه میکنید ؟!

علیرضا مداح
جمعه 25 مرداد 1387, 13:44 عصر
سلام دوستان عزیز،
علاوه بر موارد ذکر شده ، یکی از معایب expose کزدن یکی از کنترل های فرم به صورت public این است که در صورتی که در حین روند پروژه تصمیم بر این گرفته شود که کنترل مورد نظر با یک کنترل دیگر جایگزین گردد ، در اینصورت تمامی کدهای Consumer باید تغییر کند ، بنابراین نباید کنترلهای یک فرم به طور مستقیم در دسترس باشند ، این مسئله به ویژه در پروژه های Teamwork بیشتر نمود پیدا میکند ،/

Mahdi.Kiani
جمعه 25 مرداد 1387, 14:51 عصر
شما به من بگو آیا مایکروسافت که حکم ClassDesigner رو داشته برای برنامه نویسان، از این بابت نگرانی نداشته که DataSet.Tables رو در اختیار کاربران قرار بده ؟ چون ممکنه کسی myTable رو dispose کنه در حالی که توی همون فرم بهش نیاز داره!



MyTable را شما ایجاد کرده اید. نه ماکروسافت..پس حق این را دارید که هر عمل مجازی که برای آن تعریف شده است انجام دهید..

اما، Label ای که شما حق دسترسی کامل اون را به مصرف کننده کلاس دادید، جزء Class Creator می باشد.. یعنی Label جزئی از تعریف فرم1 شما می باشد.. پس نباید از بیرون، دسترسی های غیر مجاز به آن داشت..





نمیدونم چرا شما گیر دادی که کسی dispose نکنه، اگر کسی بخواد کنترلی رو در فرم دیگه dispose کنه، مشکل اینه که هنوز مسلط به برنامه نویسی نیست، باید بره برنامه نویسی رو یاد بگیره، و گرنه هیچ کس کلاسهای داخلی یک کلاس بیرونی رو dispose نمیکنه (این یکی از نکات اصلی برنامه نویسی OOP هست)




متاسفانه، مشکل همین هست که در پست قبلی هم مطرح کردم..
وقتی شخصی در یک پروژه هم Designer باشد، هم Consumer ، طبیعتا نمی تواند به خوبی، مشکلاتی که ممکن است بر اثر چنین اشتباهاتی ایجاد شود را درک کند.. یا اینکه درک می کند و چون به قول شما، عمل غیر مجازی بر روی آبجکت ها انجام نمی دهد، پس فکر می کند که مشکلی وجود ندارد..

*********
عمل Dispose فقط یک مثال بود.. صرفا بحث سر Dispose کردن یا نکردن نیست...
وقتی شما دستزسی کامل می دهید، یعنی اینکه consumer شما هر عملی که بخواهد می تواند بر سر آبجکت شما بیاورد..

گاهی مواقع، این دسترسی ها نه تنها بر روی خود آبجکت مذکور، بلکه بر روی دیگر آبجکت ها نیز می تواند تاثیر بگذارد و عملکرد آن ها را تحت تاثیر قرار دهد..

نمونه برنامتون را با کمی تغییر آپلود می کنم که ببینید که چه مشکلاتی ممکن است پیش آید..
پس از فشردن دکمه ببر روی فرم2، Button ای که بر روی فرم1 قرار دارد، دیگر قابل دسترسی نخواهد بود..
و همه این مشکلات ، از آنجایی ناشی می شود که consumer کلاس شما، دسترسی به همه خواص آبجکت label را دارد.. و از همه مهمتر این که این نوع دسترسی ها کنترل شده نیست..




شما دسترسی به خاصیت یک TextBox رو با به اشتراک گذاری پسورد یک سیستم مقایسه میکنید ؟!



مشکل سر خاصیت Text و یا دیگر خواص نیبست... مشکل اینجاست که کلاس X اگر نیاز دارد که بتواند به خاصیت a از آبجکتی دسترسی پیدا کند، نباید این اجازه را داشته باشد که بتواند دیگر خواص اون آبجکت را تحت تاثیر رفتار خودش قرار دهد..

اَرژنگ
جمعه 25 مرداد 1387, 18:02 عصر
شما دسترسی به خاصیت یک TextBox رو با به اشتراک گذاری پسورد یک سیستم مقایسه میکنید ؟!
فرق نمیکنه، اگر قرار است که یک چیزی فقط مطعلق به یک شیئ باشد (چه کاربر و یا چه برنامه) وقتی که دسترسی بهش پابلیک باشد، یعنی اینکه دارد آگهی میده که از هر جایه برنامه بهش دسترسی کنند. اتفاقا مثال خوبی است که چرا با اینکه یک مدیر یک سیستم اگر بخواد میتواند پسورد کاربر را عوض کند ولی هنوز پسورد کاربر فقط باید برایه کاربر محفوظ بماند.

hdv212
جمعه 25 مرداد 1387, 20:00 عصر
MyTable را شما ایجاد کرده اید. نه ماکروسافت..پس حق این را دارید که هر عمل مجازی که برای آن تعریف شده است انجام دهید..
آیا به نظر شما این کار با منطق OOP جور در میاد ؟ یعنی مشکلی نیست اگه من myTable رو dispose کنم ؟ در صورتی که ممکنه جای دیگه از اون استفاده شده باشه ؟
در ضمن، مگه کنترلی که روی فرم میکشم رو خودم ایجاد نکردم ؟


اما، Label ای که شما حق دسترسی کامل اون را به مصرف کننده کلاس دادید، جزء Class Creator می باشد.. یعنی Label جزئی از تعریف فرم1 شما می باشد.. پس نباید از بیرون، دسترسی های غیر مجاز به آن داشت..
من دسترسی فقط در حیطه ی همون Assembly رو دادم (Internal)، در ضمن شما امتحان کن ببین با Public کردن دسترسی یک کنترل، در فرم دیگه میتونی مقدار Text اونو تغییر بدی یا Dispose کنی.
در ضمن کلاس Label برای کلاس فرم، حکم همون کلاس DataTableCollection,... رو داره برای کلاس DataSet، مگه DataTableCollection خارج از جزء Class Deigner در DataSet هست ؟


گاهی مواقع، این دسترسی ها نه تنها بر روی خود آبجکت مذکور، بلکه بر روی دیگر آبجکت ها نیز می تواند تاثیر بگذارد و عملکرد آن ها را تحت تاثیر قرار دهد..

نمونه برنامتون را با کمی تغییر آپلود می کنم که ببینید که چه مشکلاتی ممکن است پیش آید..
پس از فشردن دکمه ببر روی فرم2، Button ای که بر روی فرم1 قرار دارد، دیگر قابل دسترسی نخواهد بود..
و همه این مشکلات ، از آنجایی ناشی می شود که consumer کلاس شما، دسترسی به همه خواص آبجکت label را دارد.. و از همه مهمتر این که این نوع دسترسی ها کنترل شده نیست..
اینکه بر روی هر آبجکتی ممکنه اثر بذاره، کاملا بستگی به منطق برنامه و کدنویسی و شیوه ی طراحی نرم افزار داره، شما میتونی با چاقو هم میوه پوست بکنی و هم آدم بکشی، دلیلی نداره با تغییر دسترسی یک کنترل بدبینانه به موضوع نگاه کنیم و همه ی نیزه ها رو به سمت Class Designer بچرخونیم، من برنامه ی شما کمی تغییر دادم تا ببینید این شیوه کاملا بستگی به منطق برنامه نویسی داره، کدی که در رویداد فرم 2 اجرا میشه، در فرم1 هم همون نتیجه رو داره، ربطی به دسترسی کنترل نداره، هدف و شیوه ی کدنویسی اشتباهه.


فرق نمیکنه، اگر قرار است که یک چیزی فقط مطعلق به یک شیئ باشد (چه کاربر و یا چه برنامه) وقتی که دسترسی بهش پابلیک باشد، یعنی اینکه دارد آگهی میده که از هر جایه برنامه بهش دسترسی کنند. اتفاقا مثال خوبی است که چرا با اینکه یک مدیر یک سیستم اگر بخواد میتواند پسورد کاربر را عوض کند ولی هنوز پسورد کاربر فقط باید برایه کاربر محفوظ بماند.
اولا من دسترسی public ندادم، ثانیا چند خط قبل گفتم، شما ببین اگه دسترسی Textbox رو در فرم 1 public
کنی میتونی با این کد مقدار Text اونو از فرم 2 عوض کنی :

objForm1.textBox1.Text = "Changed! from Form2";

علیرضا مداح
جمعه 25 مرداد 1387, 20:48 عصر
اینکه بر روی هر آبجکتی ممکنه اثر بذاره، کاملا بستگی به منطق برنامه و کدنویسی و شیوه ی طراحی نرم افزار داره،

در صورتیکه شما در یک سازمان تنها Class Creator باشید و کدهای نوشته شده توسط شما بنا باشد تا در چندین پروژه متفاوت مورد استفاده قرار گیرد که شما در آنها شرکت نداشته و در نتیجه از شرایط آن پروژه ها اطلاعی ندارید ، آنوقت نمیتوان چنین نظری داد ، چون هر پروژه شرایط خاص خود را داشته و بنابراین باید از یک روش اصولی و منطقی که در هر شرایطی و در هر پروژه ای مشکل ساز نباشد ، بهره برد ، مایکروسافت نیز هنگامیکه اسمبلی های دات نت فریم ورک را طراحی میکند ، از یک سری قوانین و اصول بنیادین پیروی مینماید تا در هر شرایطی کدهای نوشته شده منجر به اخلال در پروژه نگردد ،
روشی نیز که از طرف بنده و دوستان دیگر در این خصوص ذکر شد ، روشی است که برپایه ی اصول برنامه نویسی OOP بوده و از سوی دیگر برنامه نویسان حرفه ای دنیا نیز پیشنهاد میگردد ،
نقض یک اصل یا یک قانون ممکن است که در یک پروژه نه چندان عظیم مورد توجه نبوده و به ظاهر مشکل ساز نباشد ، اما از ویژگیهای یک برنامه نویس ، آینده نگری اوست و به مسائل باید واقع گرایانه و به تعبیری بدبینانه نگاه کند تا از تبعات آتی آن جلوگیری نماید ،/

hdv212
شنبه 26 مرداد 1387, 00:09 صبح
در صورتیکه شما در یک سازمان تنها Class Creator باشید و کدهای نوشته شده توسط شما بنا باشد تا در چندین پروژه متفاوت مورد استفاده قرار گیرد که شما در آنها شرکت نداشته و در نتیجه از شرایط آن پروژه ها اطلاعی ندارید ، آنوقت نمیتوان چنین نظری داد ، چون هر پروژه شرایط خاص خود را داشته و بنابراین باید از یک روش اصولی و منطقی که در هر شرایطی و در هر پروژه ای مشکل ساز نباشد ، بهره برد ، مایکروسافت نیز هنگامیکه اسمبلی های دات نت فریم ورک را طراحی میکند ، از یک سری قوانین و اصول بنیادین پیروی مینماید تا در هر شرایطی کدهای نوشته شده منجر به اخلال در پروژه نگردد ،
روشی نیز که از طرف بنده و دوستان دیگر در این خصوص ذکر شد ، روشی است که برپایه ی اصول برنامه نویسی OOP بوده و از سوی دیگر برنامه نویسان حرفه ای دنیا نیز پیشنهاد میگردد ،
نقض یک اصل یا یک قانون ممکن است که در یک پروژه نه چندان عظیم مورد توجه نبوده و به ظاهر مشکل ساز نباشد ، اما از ویژگیهای یک برنامه نویس ، آینده نگری اوست و به مسائل باید واقع گرایانه و به تعبیری بدبینانه نگاه کند تا از تبعات آتی آن جلوگیری نماید
مایکروسافت هم زمانی که میخواست کلاس DataSet رو بسازه، مقرر کرد که خاصیت Tablesبه صورت public تعریف بشه، برنامه نویسان باید اینو بدونن که این خاصیت به صورت public وجود داره و هرگونه استفاده ی ناشایست از این کلاس(Tables) تبعات سختی رو متوجه برنامه شون خواهد کرد پس باید با چشمان باز از اون استفاده کنن، ولی این عمل ممکنه باعث سوء استفاده ی برخی از برنامه نویسان(حالا چه عمدی و چه سهوی) بشه، آیا تقصیر مایکروسافته که این خاصیت رو در DataSet به صورت public معرفی کرده ؟

پس ممکنه این کلاس به خاطر وجود اعضای public (و احیانا استفاده ی نابجا از این اعضا) در آینده مشکل ساز بشه!


روشی نیز که از طرف بنده و دوستان دیگر در این خصوص ذکر شد ، روشی است که برپایه ی اصول برنامه نویسی OOP بوده و از سوی دیگر برنامه نویسان حرفه ای دنیا نیز پیشنهاد میگردد ،
بله درسته، بر مبنای همون روش، مشکلی که آقای کیانی عزیز مطرح کردن، عرض کردم با استفاده از Propertyای که اون خاصیت مورد نظرمون رو Encapsulate بکنه حل میشه.
ولی یه سوال، برنامه نویسان حرفه ای دنیا این شیوه رو پیشنهاد کردند یا شیوه های دیگه رو غلط معرفی کردند ؟

علیرضا مداح
شنبه 26 مرداد 1387, 09:36 صبح
مایکروسافت هم زمانی که میخواست کلاس DataSet رو بسازه، مقرر کرد که خاصیت Tablesبه صورت public تعریف بشه، برنامه نویسان باید اینو بدونن که این خاصیت به صورت public وجود داره و هرگونه استفاده ی ناشایست از این کلاس(Tables) تبعات سختی رو متوجه برنامه شون خواهد کرد پس باید با چشمان باز از اون استفاده کنن، ولی این عمل ممکنه باعث سوء استفاده ی برخی از برنامه نویسان(حالا چه عمدی و چه سهوی) بشه، آیا تقصیر مایکروسافته که این خاصیت رو در DataSet به صورت public معرفی کرده ؟

پس ممکنه این کلاس به خاطر وجود اعضای public (و احیانا استفاده ی نابجا از این اعضا) در آینده مشکل ساز بشه!



صحیح میفرمایید ، بنده مخالفتی با این موضوع ندارم و در واقع مثال DataSet از جانب بنده مطزح نشد ، در بسیازی از سازمانها هنگام طراحی معماری چند لایه بدینصورت عمل میشود که یکسری کلاس واسط میان DataSet و اشیاء آن و Class Consumer در سمت کلاینت ایجاد میگردد و اعضای تیم ارتباط مستقیمی با شیء DataTable ندارند و امکان آن وجود دارد که در آینده DataSet با یک شیء دیگر جهت دسترسی به داده جایگزین شده و از مدل دیگری جهت دسترسی به داده ها استفاده گردد ، در آنصورت تنها کافیست که کدهای Class Creator تغییر یابند.


ولی یه سوال، برنامه نویسان حرفه ای دنیا این شیوه رو پیشنهاد کردند یا شیوه های دیگه رو غلط معرفی کردند ؟
برای رسیدن به یک هدف ، همواره یک روش بهتر وجود دارد ، همیشه باید روشی انتخاب گردد که کمترین میزان خطا را در حالت کلی و در هر شرایطی داشته یاشد و روش ذکر شده که مبتنی بر اصل Encapsulation میباشد ، در شرایط کلی ، نتایج بهتری را بدست میدهد و مشکلاتی که پیش از این ذکر شد را به وجود نمی آورد و به همین خاطر اگر بخواهیم منطبق بر قوانین OOP عمل کنیم و این دو روش را نسبت به هم بررسی کینم ، روش تغییر Modifier - مجددا" تکرار میکنم در حالت کلی - صحیح نخواهد بود ،

پ.ن : از مهدی ، حامد ، آرژنگ و linux به سبب شرکت در این بحث تشکر میکنم و امیدوارم از این دست گفتگوها در آینده بیشتر به وجود بیاید ،

Mahdi.Kiani
شنبه 26 مرداد 1387, 11:19 صبح
مایکروسافت هم زمانی که میخواست کلاس DataSet رو بسازه، مقرر کرد که خاصیت Tablesبه صورت public تعریف بشه، برنامه نویسان باید اینو بدونن که این خاصیت به صورت public وجود داره و هرگونه استفاده ی ناشایست از این کلاس(Tables) تبعات سختی رو متوجه برنامه شون خواهد کرد پس باید با چشمان باز از اون استفاده کنن، ولی این عمل ممکنه باعث سوء استفاده ی برخی از برنامه نویسان(حالا چه عمدی و چه سهوی) بشه، آیا تقصیر مایکروسافته که این خاصیت رو در DataSet به صورت public معرفی کرده ؟

پس ممکنه این کلاس به خاطر وجود اعضای public (و احیانا استفاده ی نابجا از این اعضا) در آینده مشکل ساز بشه!




مشکل اینجاست که همه چیز را دارید با هم قاطی میکنید.. خاصیت Tabel ای ازش صحبت فرمودید، به مانند یک ظرف خالی می میاند که شما می توانید داده های خود را درون آن نگه داری کنید..
دقیقا مانند خاصیت Items از کنترل های دیگر..
شما می توانید داده هایتان را به درون این ظرف بریزید و یا از آن خارج کنید.. نکته مهم اینجاست که در هیچ یک از این حالات ماهیت خود ظرف تحت تاثیر قرار نمی گیرد..

می توانید Tabel هایی را به DataSet اضافه کندی، حذف کنید و... که در همه این ها دارید با داده های خودتان کار می کنید... وقتی عمل Cleare را بر روی Tabels انجام می دهید، در واقع داده هایی که از قبل وارد این ظرف کرده بودید را دارید خالی می کنید . این عمل هیچ تاثیری بر روی خود ماهیت Tabels ندارد..



شما ببین اگه دسترسی Textbox رو در فرم 1 public
کنی میتونی با این کد مقدار Text اونو از فرم 2 عوض کنی :

objForm1.textBox1.Text = "Changed! from Form2";

مادامی که شما ، یک ارجاع به شی داشته باشید، خواهید توانست به فیلد های Public آن دسترسی داشته باشید...
اگر همین TextBox ای که می فرمایید، در فرم دیگری باشد، به راحتی می توان با کد زیر به آن دسترسی داشت که باز نا صحیح می باشد



ّForm2 f2 =new Form2();
f2.textBox1.Text="some data";



***********************************************

هیچ کسی مخالف با وجود مقدار Public برای خاصیت Modifiers کنترل ها نمی باشد.. چون اگر چنین چیزی بود، دیگر برنامه نویسی OOP معنا نداشت..
و در هیچ یک از پست های این تاپیک نیز، چنین چیزی مشاهده نمی شود و هر جا هم که گفته شده public نه، در ادامه گفته شده استفاده نا بجا.. یعنی استفاده نا صحیح از یک خاصیت برای رسیدن به یک مقصود.. کاری که بسیاری برنامه نویسان انجام می دهند و خوب گاها و در کوتاه مدت برنامشون به مشکلی بر نخواهد خورد و حالا به دلایل مختلفی از جمله:
بی اطلاعی از روش های دیگر
بی اطلاعی از معایب روشی که استفاده کردند
در ظاهر، زود جواب گرفتن و رسیدن به مقصود
و...
آن راه حل ها را نیز به دیگران پیشنهاد می کنند..

***
تمامی بحث این تاپیک بر روی این موضوع بود که برای تغذیه مقدار Text ، روشی که استفاده و پیشنهاد دادید، غیر استاندارد و خلاف منطق OOP بود که بعضی از ایرادات آن را با نمونه مثال برایتان تشریح کردم..

چندین بار عرض کردم که :



وقتی فقط قراره text یک textbox از جای دیگری تغذیه شود، معنایی ندارد که backColor آن هم قابل دسترسی باشد..



و نکته مهمتر اینکه، فرم2 ، چه نیازی دارد که بداند، داده ای که برای آبجکت های دیگر می فرستد، به چه منظور می فرستد؟

ما تنها نیاز داریم، که داده ای را از فرم2 یا آبجکت های دیگر دریافت کنیم، حال این مربوط به میشود که از آن داده چگونه استفاده کنم..

فرض کنید در جایی از برنامه، (بنا به منطق برنامه)بخواهد به فرم2 دسترسی پیدا کنید ( آن را نمایش دهید) ولی نیازی نباشد، داده جدید و تغییر داده شده در Form2 به Label در فرم1 انتقال پیدا کند..

در روشی که شما بیان کردید، به دلیل اینکه Label را به Form2 وابسته کردید، امکان این کار وجود ندارد(یا اینکه باز باید دست به دامان روش های ناصحیح شویم).. ولی در روشی که من نمونه مثال آن را هم فرستادم، شما تنها یک Event را هندل می کنید که به جدید ترین داده فرم2، در فرم1، دسترسی دارید که می توانید هر عملی با آن انجام دهید( انتساب به Label ، چشم پوشی از آن و ...)

hdv212
یک شنبه 27 مرداد 1387, 02:40 صبح
فکر میکنم این برنامه دیگه منطبق با منطق OOP باشه.