الگوی Template method

بعضی ار مردم نمی توانند زندگی را بدون قهوه تصور کنند و بعضی دیگر زندگی را بدون چای نمی توانند تصور کنند. ولی جزء تشکیل دهنده اصلی هر دو کافئین است. شباهت های دیگر نیز بین این دو مورد وجود دارد. روش ساخت هر دوی آنها تقریبا مشابه است. شما اغلب موارد به ترتیب زیر عمل می کنید.

دستوالعمل ساخت قهوه:

1.       مقداری آب را می جوشانید.

2.       مقدار قهوه در آب جوشانده شده می ریزد تا دم بکشد.

3.       فهوه را در فنجان می ریزد.

4.       مقداری شکر و یا شیر به آن اضافه می کنید.

دستورالعمل ساخت چای:

1.       مقداری آب را می جوشانید.

2.       مقدار چای خشک در آب جوشانده شده می ریزد تا دم بکشد.

3.       چای را در فنجان می ریزد.

4.       مقداری شکر به آن اضافه می کنید.

 

اگر بخواهیم برنامه ای برای تهیه چای و قهوه بنویسیم کلاس های را به صورت زیر خواهیم داشت.

 

کلاس قهوه

Public Class Coffee

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

    Public Sub prepareRecipe()

        مراحل تهیه قهوه

        boilWater()

        brewCoffeeGrinds()

        pourInCup()

        addSugereAndMilk()

    End Sub

    Public Sub boilWater()

        Console.WriteLine(جوشاندن آب)

    End Sub

    Public Sub brewCoffeeGrinds()

        Console.WriteLine(ریختن پودر قهوه به داخل آب جوشانده شده)

    End Sub

    Public Sub pourInCup()

        Console.WriteLine(ریختن قهوه به فنجان)

    End Sub

    Public Sub addSugereAndMilk()

        Console.WriteLine(اضافه کردن شیر و شکر)

    End Sub

End Class

 

 

کلاس چای

Public Class Tea

    Public Sub prepareRecipe()

        boilWater()

        brewTea()

        pourInCup()

        addSugere()

    End Sub

    Public Sub boilWater()

        Console.WriteLine(جوشاندن آب)

    End Sub

    Public Sub brewTea()

        Console.WriteLine(ریختن چای به داخل آب جوشانده شده)

    End Sub

    Public Sub pourInCup()

        Console.WriteLine(ریختن چای به فنجان)

    End Sub

    Public Sub addSugere()

        Console.WriteLine(اضافه کردن شکر)

    End Sub

End Class

 

 با مشاهده دو کلاس بالا مشاهده می شود که دو متد boilWater و pourInCup دقیقا مشابه یکدیگر هستند. پس طراحی ما دارای اشتباه هست چون بعضی از کدها تکرار شده اند. پس ما باید طراحی خود را تغییر دهیم. ما می توانیم طراحی خود را به صورت زیر تغییر دهیم. دو متد کاملا مشابه در کلاس پایه پیاده سازی می شود. اما چون متد prepareRecipe در هر کلاس به صورت نتفاوت عمل می کند. این متد در زیر کلاس های مربوطه پیاده سازی می شود.

طراحی بالا یک طراحی خوب است اما نمی شود طراحی را بهتر از این کرد؟   اگر توجه کنیم متوجه می شویم که برای تهیه هر دو مورد الگوریتم یکسانی را به کار می بریم:

1.       جوشاندن آبی

2.       اضافه کردن چای یا قهوه به آب جوشیده شده

3.       ریختن نوشیدنی به دست امده در فنجان

4.       اضافه کردن چاشنی مورد نظر به نوشیدنی

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

 Public Sub prepareRecipe()

        boilWater()

        brewTea()

        pourInCup()

        addSugere()

 End Sub

 

Public Sub prepareRecipe()

        boilWater()

        brewCoffeeGrinds()

        pourInCup()

        addSugereAndMilk()

End Sub

 

 همانطوریکه می توانید مشاهده کنید کلاس مر بوط به قهوه متدهای به نام brewCoffeeGrinds و addSugereAndMilk را استفاده می کند در حالیکه کلاس مربوط به چای از متد های به نام brewTea و addSugere استفاده می کند. یک راه حل این است که برای هر مرحله غیر مشابه یک نام مشترک در نظر بگیریم. نام متدهای brewTea و brewCoffeeGrinds را به brew تغییر دهیم. و نام متدهای addSugereAndMilk و addSugere را به addCondiments  تغییر می دهیم. پس متد prepareRecipe برای هر دو کلاس به صورت زیر تغییر می کند.

Public Sub prepareRecipe()

        boilWater()

        brew ()

        pourInCup()

        addCondiments()

End Sub

 

 پس حالا می توانیم این متد را بطور کامل به کلاس پایه منتقل کنیم و طراحی را به صورت زیر تغییر دهیم.

حالا ما برای این مسله به یک طراحی ائده ال دست یافتیم. کاری که ما برای حل این مسله انجام دادیم به نام الگوی Template method  شناخته می شود. دلیل نامگذاری این الگو را می توانیم با مشاهده متد prepareRecipe از کلاس پایه درک کنیم. اولین اینکه prepareRecipe یک متد است و دوما به عنوان یک قالب برای الگوریتم به کار می رود. برای نمونه در این مثال شامل الگوریتم تهیه یک نوشیدنی می باشد.

الگوی Template method، مراحل انجام یک الگوریتم را در یک متد در کلاس پایه تعریف می کند و اجازه می دهد زیر کلاس ها یک یا چند مرحله از الگوریتم را پیاده سازی کنند. در واقع اسکلت یک الگوریتم در یک متد تعریف می شود.

هدف ما در این الگو، ایجاد یک قالب برای یک الگوریتم است. یک قالب یک الگوریتم را به صورت مجموعه ای از مراحل تعریف می کند. هر کدام از این مراحل به عنوان یک متد در نظر گرفته می شود. که بعضی از متدها در همان کلاس پایه پیاده سازی می شود و بعضی از متدها به صورت abstract در کلاس پایه در نظر گرفته می شود و در زیر کلاس ها پیاده سازی می شود.

نمودار UML :

نمودار UML این الگو به صورت بالا است. که در آن کلاس AbstractClass یک کلاس Abstract  است. که الگوی قالب در آن تعریف می شود. و متد primitiveOperation یک متد Abstract  است (یک مرحله از الگوریتم) که در زیر کلاس پیاده سازی خواهد شد. همانطوریکه در مثال بالا مشاهده کردیم می تواند بیش از یک کلاس ConcerteClass وجود داشته باشد. این حالت زمانی رخ می دهد که بعضی از مراحل الگوریتم بتواند در روش های مختلف پیاده سازی شود.

سال نو

با تاخیر چند روزه، سال نو را به همه دوستان تبریگ گفته و آروزی سالی سر شار از موفقیت را برای آنها دارم.

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

الگوی زنجیره مسئولیت (Chain of Responsibility pattern)

یک سرویس دهنده اینترنتی را در نظر بگیرید. این شرکت دارای سه سطح پشتیبانی به شرح زیر برای کاربران است:

سطح 1: در این سطح به مشکلات ابتدایی کاربران مانند فراموش کردن کلمه عبور کاربران و … رسیدگی می شود.

سطح 2: اگر اعضای گروه سطح 1 نتوانند مشکل مورد نظر را حل کنند. مشکل برای حل به گروه سطح 2 ارجاع داده می شود.

سطح 3: اگر اعضای گروه 2 نیز نتوانند مشکل مورد نظر را حل کنند.مشکل برای حل به گروه سطح 3 ارجاع داده می شود. در این سطح برای حل مشکل یک قرار ملاقات در محل مشکل با مشتری گذاشته می شود.

همانطوریکه در مثال بالا مشخص است. ممکن است هر کدام از گروه ها به در خواست ارائه شده پاسخ دهند. ولی دقیقا مشخص نیست کدام گروه به در خواست ارائه شده پاسخ خواهد داد. اما همه گروه ها باید شانس این را داشته باشند که به درخواست ارائه شده پاسخ دهند. این شانس اولویت دار است. برای نمونه در مثال بالا ابتدا به تیم سطح 1 این شانس داده می شود تا مشکل را حل کند. در صور ت عدم حل مشکل به ترتیب، شانس به تیمهای 2 و 3 داده می شود. این امکان نیز وجود دارد که هیچ یک از تیم ها نتوانند این مشکل را حل کنند و درخواست ارائه شده بدون پاسخ بماند.

مثالی که در بالا ارائه شده تقریبا تعریفی از الگوی Chain of responsibility (زنجیره مسئولیت) می باشد.

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

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

سطوح مدیریت

مبلغ سفارش

مدیر نمایندگی

25000

مدیر ناحیه

100000

نايب‌ رئيس‌

200000

رئيس‌

400000

 

شما برای اینکار چه الگوی را پیشنهاد می کنید؟

اجاز ه بدهید کار را با الگوی زنجیره مسولئیت ادامه دهیم. در ابتدا یک کلاس برای سفارش به نام سفارش خرید در نظر می گیریم.

سپس یک کلاس انتزاعی به نام مدیریت سفارش تعریف می کنیم که دارای یک اینترفیس مشترک برای هر کدام از سطوح مدیریت است. که نمودار کلاس  مربوط به مدیریت سفارش و سطوح مدیریت به صورت زیر خواهد بود. که متد تعیین شی جانشین (SetSuccessor)، برای مشخص کردن شی بعدی (شی جانشین) در زنجیره عمل می کند.

برای تائید یک سفارش، کارهای زیر صورت خواهد گرفت:

1.    ایجاد یک مجموعه از اشیای که می توانند به درخواست های رسیده شده پاسخ بدهند (سطوح مدیریت). و قرار دادن آنها در یک زنجیره به طور مرتب بر حسب مقادیری که می توانند تائید کنند. هر یک از این اشیاء توسط متد SetSuccessor به شی بعدی متصل می شود.(کلاس Main)

2.       یک درخواست تائید به اولین شی موجود در زنجیره ارسال می شود که این کار توسط فراخوانی متد   authorize  آن شی انجام می شود. اگر مبلغ سفارش از مقدار مبلغی که ان شی نی تواند تائید کند کوچکتر باشد، آنرا تائید می کند در غیر اینصورت آن درخواست را به شی بعدی در زنجیره ارسال می کند. (برای مثال در کد زیر می توانید کلاس BranchManager را بررسی کنید. ) 

 

کلاس مدیریت سفارش

abstract class RHandler

    {                                     

        protected RHandler successor;

 

        public void SetSuccessor(RHandler successor)

        {

            //تعیین شی جانشین

            this.successor = successor;

        }

 

        public abstract void authorize (PurchaseRequest purchase);

    }

کلاس مدیر نمایندگی

 

class BranchManager: RHandler
  {
   

 public override void authorize (PurchaseRequest purchase)
    {
   // تائید سفارش

      if (purchase.Amount <=25000)
      {

       

      }
      else if (successor != null)
      {
        successor.ProcessRequest(
RegionalDirector);
      }
    }
  }

کلاس Main

class MainApp

    {

        static void Main()

        {

            BranchManager A = new BranchManager();

            RegionalDirector B = new RegionalDirector();

            VicePresident C = new VicePresident();

            President D = new President();

            A.SetSuccessor(B);

            B.SetSuccessor(C);

            C.SetSuccessor(D);

 

            Purchase p = new Purchase( 1, “Order 1”,15000);

            A.authorize(p);

 

            Purchase p = new Purchase( 2, “Order 2”,110000);

            A.authorize(p);

        }

    }

 

 

دیاگرام کلاس الگو:

برای بچه های بزرگ

روباه گفت: سلام.
شهریار کوچولو برگشت اما کسی را ندید. با وجود این با ادب تمام گفت: سلام.
صداگفت: من این‌جام، زیر درخت سیب…
شهریار کوچولو گفت: کی هستی تو؟ عجب خوشگلی!
روباه گفت: یک روباهم من.
شهریار کوچولو گفت: بیا با من بازی کن. نمی‌دانی چه قدر دلم گرفته…
روباه گفت: نمی‌توانم بات بازی کنم. هنوز اهلیم نکرده‌اند آخر.
شهریار کوچولو آهی کشید و گفت: معذرت می‌خواهم.
اما فکری کرد و پرسید: اهلی کردن یعنی چه؟
روباه گفت: تو اهل این‌جا نیستی. پی چی می‌گردی؟
شهریار کوچولو گفت: پی آدم‌ها می‌گردم. نگفتی اهلی کردن یعنی چه؟
روباه گفت: آدم‌ها تفنگ دارند و شکار می‌کنند. اینش اسباب دلخوری است! اما مرغ و ماکیان هم پرورش می‌دهند و خیرشان فقط همین است. تو پی مرغ می‌کردی؟
شهریار کوچولو گفت: نه، پیِ دوست می‌گردم. اهلی کردن یعنی چی؟
روباه گفت: یک چیزی است که پاک فراموش شده. معنیش ایجاد علاقه کردن است.
ایجاد علاقه کردن؟
روباه گفت: معلوم است. تو الان واسه من یک پسر بچه‌ای مثل صد هزار پسر بچه‌ی دیگر. نه من هیچ احتیاجی به تو دارم نه تو هیچ احتیاجی به من. من هم واسه تو یک روباهم مثل صد هزار روباه دیگر. اما اگر منو اهلی کردی هر دوتامان به هم احتیاج پیدا می‌کنیم. تو واسه من میان همه‌ی عالم موجود یگانه‌ای می‌شوی من واسه تو.
شهریار کوچولو گفت: کم‌کم دارد دستگیرم می‌شود. یک گلی هست که گمانم مرا اهلی کرده باشد.
روباه گفت: بعید نیست. رو این کره‌ی زمین هزار جور چیز می‌شود دید.
شهریار کوچولو گفت: اوه نه! آن رو کره‌ی زمین نیست.
روباه که انگار حسابی حیرت کرده بود گفت: رو یک سیاره‌ی دیگر است؟
آره.
تو آن سیاره شکارچی هم هست؟
نه.
محشر است! مرغ و ماکیان چه‌طور؟
نه.
روباه آه‌کشان گفت: همیشه‌ی خدا یک پای بساط لنگ است!
اما پی حرفش را گرفت و گفت: زندگی یک‌نواختی دارم. من مرغ‌ها را شکار می‌کنم آدم‌ها مرا. همه‌ی مرغ‌ها عین همند همه‌ی آدم‌ها هم عین همند. این وضع یک خرده خلقم را تنگ می‌کند. اما اگر تو منو اهلی کنی انگار که زندگیم را چراغان کرده باشی. آن وقت صدای پایی را می‌شناسم که باهر صدای پای دیگر فرق می‌کند: صدای پای دیگران مرا وادار می‌کند تو هفت تا سوراخ قایم بشوم اما صدای پای تو مثل نغمه‌ای مرا از سوراخم می‌کشد بیرون. تازه، نگاه کن آن‌جا آن گندم‌زار را می‌بینی؟ برای من که نان بخور نیستم گندم چیز بی‌فایده‌ای است. پس گندم‌زار هم مرا به یاد چیزی نمی‌اندازد. اسباب تاسف است. اما تو موهات رنگ طلا است. پس وقتی اهلیم کردی محشر می‌شود! گندم که طلایی رنگ است مرا به یاد تو می‌اندازد و صدای باد را هم که تو گندم‌زار می‌پیچد دوست خواهم داشت…
خاموش شد و مدت درازی شهریار کوچولو را نگاه کرد. آن وقت گفت: اگر دلت می‌خواهد منو اهلی کن!
شهریار کوچولو جواب داد: دلم که خیلی می‌خواهد، اما وقتِ چندانی ندارم. باید بروم دوستانی پیدا کنم و از کلی چیزها سر در آرم.
روباه گفت: آدم فقط از چیزهایی که اهلی کند می‌تواند سر در آرد. انسان‌ها دیگر برای سر در آوردن از چیزها وقت ندارند. همه چیز را همین جور حاضر آماده از دکان‌ها می‌خرند. اما چون دکانی نیست که دوست معامله کند آدم‌ها مانده‌اند بی‌دوست… تو اگر دوست می‌خواهی خب منو اهلی کن!
شهریار کوچولو پرسید: راهش چیست؟
روباه جواب داد: باید خیلی خیلی حوصله کنی. اولش یک خرده دورتر از من می‌گیری این جوری میان علف‌ها می‌نشینی. من زیر چشمی نگاهت می‌کنم و تو لام‌تاکام هیچی نمی‌گویی، چون تقصیر همه‌ی سؤِتفاهم‌ها زیر سر زبان است. عوضش می‌توانی هر روز یک خرده نزدیک‌تر بنشینی.

فردای آن روز دوباره شهریار کوچولو آمد.
روباه گفت: کاش سر همان ساعت دیروز آمده بودی. اگر مثلا سر ساعت چهار بعد از ظهر بیایی من از ساعت سه تو دلم قند آب می‌شود و هر چه ساعت جلوتر برود بیش‌تر احساس شادی و خوشبختی می‌کنم. ساعت چهار که شد دلم بنا می‌کند شور زدن و نگران شدن. آن وقت است که قدرِ خوشبختی را می‌فهمم! اما اگر تو وقت و بی وقت بیایی من از کجا بدانم چه ساعتی باید دلم را برای دیدارت آماده کنم؟… هر چیزی برای خودش قاعده‌ای دارد.
شهریار کوچولو گفت: قاعده یعنی چه؟
روباه گفت: این هم از آن چیزهایی است که پاک از خاطرها رفته. این همان چیزی است که باعث می‌شود فلان روز با باقی روزها و فلان ساعت با باقی ساعت‌ها فرق کند. مثلا شکارچی‌های ما میان خودشان رسمی دارند و آن این است که پنج‌شنبه‌ها را با دخترهای ده می‌روند رقص. پس پنج‌شنبه‌ها بَرّه‌کشانِ من است: برای خودم گردش‌کنان می‌روم تا دم مُوِستان. حالا اگر شکارچی‌ها وقت و بی وقت می‌رقصیدند همه‌ی روزها شبیه هم می‌شد و منِ بیچاره دیگر فرصت و فراغتی نداشتم.

به این ترتیب شهریار کوچولو روباه را اهلی کرد.
لحظه‌ی جدایی که نزدیک شد روباه گفت: آخ! نمی‌توانم جلو اشکم را بگیرم.
شهریار کوچولو گفت: تقصیر خودت است. من که بدت را نمی‌خواستم، خودت خواستی اهلیت کنم.
روباه گفت: همین طور است.
شهریار کوچولو گفت: آخر اشکت دارد سرازیر می‌شود!
روباه گفت: همین طور است.
پس این ماجرا فایده‌ای به حال تو نداشته.
روباه گفت: چرا، واسه خاطرِ رنگ گندم.
بعد گفت: برو یک بار دیگر گل‌ها را ببین تا بفهمی که گلِ خودت تو عالم تک است. برگشتنا با هم وداع می‌کنیم و من به عنوان هدیه رازی را به‌ات می‌گویم.
شهریار کوچولو بار دیگر به تماشای گل‌ها رفت و به آن‌ها گفت: شما سرِ سوزنی به گل من نمی‌مانید و هنوز هیچی نیستید. نه کسی شما را اهلی کرده نه شما کسی را. درست همان جوری هستید که روباه من بود: روباهی بود مثل صدهزار روباه دیگر. او را دوست خودم کردم و حالا تو همه‌ی عالم تک است.
گل‌ها حسابی از رو رفتند.
شهریار کوچولو دوباره درآمد که: خوشگلید اما خالی هستید. برای‌تان نمی‌شود مُرد. گفت‌وگو ندارد که گلِ مرا هم فلان ره‌گذر می‌بیند مثل شما. اما او به تنهایی از همه‌ی شما سر است چون فقط اوست که آبش داده‌ام، چون فقط اوست که زیر حبابش گذاشته‌ام، چون فقط اوست که با تجیر برایش حفاظ درست کرده‌ام، چون فقط اوست که حشراتش را کشته‌ام (جز دو سه‌تایی که می‌بایست شب‌پره بشوند)، چون فقط اوست که پای گِلِه‌گزاری‌ها یا خودنمایی‌ها و حتا گاهی پای بُغ کردن و هیچی نگفتن‌هاش نشسته‌ام، چون او گلِ من است.
و برگشت پیش روباه.
گفت: خدانگه‌دار!
روباه گفت: خدانگه‌دار!… و اما رازی که گفتم خیلی ساده است:
جز با دل هیچی را چنان که باید نمی‌شود دید. نهاد و گوهر را چشمِ سر نمی‌بیند.
شهریار کوچولو برای آن که یادش بماند تکرار کرد: نهاد و گوهر را چشمِ سر نمی‌بیند.
ارزش گل تو به قدرِ عمری است که به پاش صرف کرده‌ای.
شهریار کوچولو برای آن که یادش بماند تکرار کرد: به قدر عمری است که به پاش صرف کرده‌ام.
روباه گفت: انسان‌ها این حقیقت را فراموش کرده‌اند اما تو نباید فراموشش کنی. تو تا زنده‌ای نسبت به چیزی که اهلی کرده‌ای مسئولی. تو مسئول گُلتی…

شهریار کوچولو برای آن که یادش بماند تکرار کرد: من مسئول گُلمَم.

 

مدلسازی پایگاه داده از روی نمودار کلاس UML

رابطه وراثت((inheritance :

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

روش اول:

در این روش برای کل سلسله مراتب کلاس، یک جدول در نظر می گیریم. که ساختار جدول به صورت زیر خواهد بود.

{صفات سوپر کلاس، صفات مختص زیر کلاس ها و یک فیلد نوع کلاس (موجودیت)}

فیلد نوع برای ذخیره اینکه رکورد مورد نظر مربوط به اطلاعات کدام کلاس است به کار می رود.

برای مثال برای نمودار بالا، ساختار زیر را خواهیم داشت:

{شماره شناسایی، نام، نام خانوادگی، مقطع، رشته، درجه، سابقه تحصیل و نوع}

همانطوریکه مشاهده می شود در جدولی با شمای بالا بعضی از فیلد برای نمونه ای از دانشجو و هم برای نمونه ای از استاد دارای مقدار NULL  خواهند بود. که یک عیب برای این روش محسوب می شود. همچنین با تغییر در صفات هر یک از کلاس ها مجبوریم جدول را دستکار کنیم که باعث خواهد شد در کلاس های دیگر نیز تغییراتی دهیم. این روش به نظر من یک روش ناکارامد می باشد. و بهتر است از این روش استفاده نشود.

 

روش دوم:

در این روش برای هر زیر کلاس یک جدول در نظر می گیریم. که شمای هر جدول به صورت زیر خواهد بود:

{صفات سوپر کلاس و صفات مختص زیر کلاس}

برای مثال برای همان نمودار مثال قبل دو جدول زیر را خواهیم داشت:

استاد{شماره شناسایی، نام، نام خانوادگی،درجه، سابقه تحصیل }

دانشجو{شماره شناسایی، نام، نام خانوادگی، مقطع، رشته }

در این روش بعضی از افزونگی ها را خواهیم داشت.برای مثال تصور کنید که شخص را داریم که هم استاد هست و هم در یک رشته دیگر به عنوان دانشجو تحصیل می کند. در این حالت صفاتی مانند نام و نام خانوادگی برای یک شخص دوباره ذخیره می شود.

اگر سوپر کلاس یک کلاس Abstract نباشد. و فقط برای زیر کلاس ها جدول در نظر بگیریم. ممکن است بعضی از اطلاعات هرگز ذخیره نشود. برای مثال یک استاد را در نظر بگیرید. که به عنوان استاد در دانشگاه در نظر گرفته شده است. اما هنوز حکم استادیش به دانشگاه ارسال نشده است.

یک عیب دیگر این روش اینست که اگر در صفات سوپر کلاس تغییراتی داده شود نیاز است که کلیه جدول های مربوط به زیر کلاس ها نیز اصلاح شود.

اما مزیت این روش نسبت به روش اول اینست که در این روش دیگر ستونهای با مقادیر Null را نخواهیم داشت.

 

روش سوم:

در این روش برای سوپر کلاس یک کلاس جداگانه در نظر می گیریم که شامل صفات سوپر کلاس می باشد. و برای هر زیر کلاس نیز یک جدول جداگانه در نظر می گیریم. که شامل صفات مختص آن زیر کلاس به همراه کلید اصلی جدول مربوط به سوپر کلاس.

برای مثال برای نمودار مثال اول، اگر صفت شماره شناسایی را برای هر شخص منحصر بفرد در نظر بگیریم.خواهیم داشت:

شخص{شماره شناسایی، نام، نام خانوادگی}

استاد{شماره شناسایی، درجه، سابقه تحصیل}

دانشجو{شماره شناسایی، مقطع، رشته}

این روش بهترین گزینه برای ما می باشد.زیرا دقیقا هر کلاس را به یک جدول جداگانه و مستقل نگاشت می کند. و هر تغییری در یک کلاس فقط در جدول مربوط به آن کلاس تاثیر خواهد گذاشت و بر خلاف دو روش قبلی، روی جدول های دیگر تاثیر نخواهد گذاشت. در این روش نه افزونگی داده داریم و نه ستونی با مقدار Null.

 

رابطه association:

با ماشین خودتان در جاده در حال حرکت هستید. نگاه می کنید و می بینید که بنزین شما در حال تمام شدن است. پس شما باید به فکر یک پمپ بنزین باشید. پس نیاز دارید درباره اطلاعات عمومی یک پمپ بنزین مانند مکان و تلفنش اطلاعاتی داشته باشید. در واقع این همان رابطه association است. در واقع این رابطه اجازه می دهد یک کلاس درباره صفات و عملیات عمومی یک کلاس دیگر اطلاعاتی داشته باشید.

اما برای نگاشت این رابطه بین دو کلاس به رابطه بین دو جدول(برای هر کلاس یک جدول در نظر می گیریم.) چه کاری باید انجام دهیم؟

دقیقا مشابه کاری را که توی پیاده سازی این رابطه انجام می دهیم. اینجا نیز انجام می دهیم. کلید اصلی جدول مربوط به کلاسی را که نیاز داریم اطلاعاتی از آن را داشته باشیم عنوان کلید خارجی استفاده می کنیم. و به جدول کلاسی که این اطلاعات را نیاز دارد اضافه می کنیم.

 

برای مثال برای نمودار شکل بالا جدول های زیر را خواهیم داشت.

آدرس{کد پست ده رقمی، شهر، خیابان و …}

شخص{کد پستی ده رقمی و صفات کلاس شخص}

 

رابطه تجمع (aggregation) و رابطه ترکیب (composition):

رابطه تجمع، یک رابطه بین یک واحد کل و جزء است. در این رابطه، بزای موجودیت کل، یک جدول و برای هر یک از کلاس های جزء نیز یک جدول طراحی می کنیم. در هر کدام از جدول های مربوط به اجزاء جزء، کلید اصلی (یا یکی از کلید های کاندید) جدول مربوط به واحد کل را می آوریم.

 

برای نمونه برای شکل بالا خواهیم داشت:

ماشین{صفات مربوط به ماشین}

تایر{کلید اصلی جدول ماشین و صفات مربوط به تایر}

موتور{کلید اصلی جدول ماشین و صفات مربوط به موتور}

در رابطه تجمع، شی جز به شی کل وابسته نیست. پس با حذف شی کل، اجزاء تشکیل دهنده آن از بین نمی روند. بلکه باید مقدار مربوط به صفت کلید شی کل در اشیاء جزء پاک شوند.

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

در اینجا من به در خواست یکی از دوستان فقط به بررسی روابط بین کلاس ها پرداختم. ولی دوستانی که به این موضوع علاقه دارند می توانند به مقاله Database Modelling in UML در سایت www.sparxsystems.com.au مراجعه کنند.

به درود همکلاسی

مرگ پایین کبوتر نیست.

مرگ وارون یک زنجره نیست.

مرگ در ذهن اقاقی جاری است.

مرگ در آب و هوای خوش اندیشه نشیمن دارد.

مرگ در ذات شب دهکده از صبح سخن می گوید.

سهراب سپهری

آیا مردن انسان چیزی بیش از برهنه بودن در باد و آب شدن در حرارت خورشید است ؟

آیا قطع شدن نفس غیر از آزاد شدن روح از سرگشتگی مدام است که از زندانش بگریزد

و در هوا بالا رفته و بدون هیچ مانعی به سوی خالقش بشتابد ؟

جبران خلیل جبران

 

اگر مرگ نبود ھمه آرزویش را می کردند ، فریادهای نا امیدی به آسمان بلند می شد ، به طبیعت نفرین می فرستادند . اگر زندگانی سپری نمی شد ، چقدر تلخ و ترسناک بود . ھنگامیکه آزمایش سخت و دشتوار زندگانی چراغھای فریبندۀ جوانی را خاموش کرده ، سرچشمه مھربانی خشک شده ، سردی ، تاریکی و زشتی گریبان گیر می گردد ، اوست که چاره می بخشد ، اوست که اندام خمیده ، سیمای پرچین ، تن رنجور را در خوابگاه آسایش می نھد .

ای مرگ ! تو از غم و اندوه زندگانی کاسته بار سنگین آنرا از دوش بر میداری ، سیه روز تیره میداری ، سیه روز تیره

بخت سرگردان را سرو سامان می دھی ، تو نوشداروی ماتم زدگی و نا امیدی می باشی ، دیده سرشکبار را خشک می گردانی . تو مانند مادر مھربانی ھستی کھ بچه
خود را پس از یک روز طوفانی در آغوش کشیده ، نوازش می کند و می خواباند ، تو زندگانی تلخ ، زندگانی درنده نیستی که آدمیان را به سوی گمراھی کشانیده و در گرداب سھمناک پرتاب می کند ، تو ھستی که بدون پروری ، فرومایگی ، خودپسندی ، چشم تنگی ، و آز آدمیزاد خندیده پرده به روی کارھای ناشایسته او می گسترانی. کیست که شراب شرنگ آگین تو را نچشد ؟ انسان چھره تو را ترسناک کرده و از تو گریزان است ، فرشته تابناک را اھریمن خشمناک پنداشته ! چرا از تو بیم

و ھراس دارد ؟ چرا به تو نارو و بھتان می زند ؟ تو پرتو درخشانی اما تاریکیت می پندارند ، تو سروش فرخنده شادمانی ھستی اما در آستانه تو شیون می کشند ، تو فرستادۀ سوگواری نیستی ،تو درمان دلھای پژمرده می باشی ، تو دریچه امید به روی نا امیدان باز می کنی ، تو از کاروان خسته و درماندۀ زندگانی مھمان نوازی کرده آنھا را از رنج راه و خستگی می رھانی ، تو سزاوار ستایش ھستی ، تو زندگانی جاویدان داری ….

صادق هدایت

 

State Pattern

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

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

برای مثال فرضی کنید با یک برنامه مانند Windows Media Player، در حال دیدن یک فیلم هستید. این برنامه دکمه های مانند Play، Pause و Stop دارد که با کلیک روی آنها می توانید برنامه را به حالت همنام با آن دکمه ببرید. پس برای این شی، سه حالت بالا را می توانید در نظر بگیرید. حال تصویر کنید که یک برنامه شبیه به مثال بالا را خودمان می خواهیم بنویسیم. یکی  از شیوه ها برای انجام این کار می تواند به این ترتیب باشد که ما در ابتدا تمام حالاتی را که یک شی Media Player، می تواند قبول کند را جمع آوری می کنیم. در مرحله دوم برای هر حالت یک متغییر تعریف می کنیم و مقادیر مربوط به آنها را مشخص می کنیم و علاوه بر اینها یک متغییر برای نگهداری حالت فعلی شی در نظر می گیریم.

const int play=0;

const int stop=1;

const int pause=2;

int state = stop; //حالت اولیه

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

public void  Stop()

{

if (state == play)

   {

    //عملیات مورد نظر

   }

if (state == pause)

   {

    //عملیات مورد نظر

   }

if (state == stop)

   {

    //عملیات مورد نظر

   }

}

روش بالا می تواند  برای پیاده سازی یک شی که دارای چندین حالت است به کار برود. ولی تصور کند که یک حالت جدید را بخواهیم به شی اضافه کنیم و یا در نحوه عملکرد شی در یک حالت خاص تغییر دهیم مطمئنا کار مشکلی را خواهیم داشت.

یک روش خوب و کارا برای پیاده سازی اشیای که در طول حیات خود می توانند چندین حالت مختلف داشته باشند، می تواند چگونه باشد؟ شاید شما پاسخ های خوب و بهتری بتوانید ارائه کنید. ولی یکی از روش ها می تواند به صورت زیر باشد:

1.       در ابتدا یک اینترفیس به نام state تعریف می کنیم که شامل یک متد برای هر عملی است که شی مورد نظر می تواند انجام دهد.

2.       در مرحله دوم برای هر حالت شی یک کلاس تعریف می کنیم که اینترفیس state را پیاده سازی می کند. در واقع این کلاس مسول پاسخگویی به رویدادها است. زمانیکه  شی در این حالت قرار دارد.

 

برای نمونه در همان مثال Media Player،  در ابتدا ما یک کلاس اینترفیس به نام state تعریف می کنیم. سپس برای هر حالت یک کلاس تعریف می کنیم که اینترفیس state را پیاده سازی می کند. برای پیاده سازی هر حالت ما نیاز داریم  تا رفتار هر کلاس را مشخص کنیم هنکامیکه هر عمل فرا خوانی می شود.

 

 

بعد از پیاده سازی تمام حالات شی مورد نظر، به کلاس اصلی یا همان کلاس شی مورد نظر (Media Player) می رسیم. این کلاس همان متد های روش اول را خواهد داشت اما با چندین تفاوت:

1.       به جای استفاده از متغییرهای عددی برای هر حالت و حالت فعلی، از اشیاء که برای حالت ها تعریف کردیم استفاده می کنیم.

 

کد جدید

کد قدیمی

public class MediaPlayer{

State MediaState;

PlayState playstate;

PauseState pausestate;

StopState stopstate;

MediaPlayer{

playstate = new PlayState();

 new PauseState ();=  pausestate

stopstate = new StopState();

MediaState = stopstate;

}

 

Public class MediaPlayer{

const int play=0;

const int stop=1;

const int pause=2;

MediaPlayer{

const int state = stop; //حالت اولیه

}

 

2.       در پیاده سازی عمل ها دیگر از جملات شرطی استفاده نمی کنیم. بلکه وقتی عملی فراخوانی می شود آن عمل به کلاس حالت فعلی برای انجام واگذار می شود.

public void  Stop()

{

MediaState.stop();

}

چون MediaState اشاره گر به حالت فعلی است. متد stop حالت فعلی اجاره خواهد شد بدون هیچ جمله ی شرطی.

  

نمودار الگوی حالت (State Pattern):

ما  تا اینجا یک الگوی حالت را بطور کامل پیاده سازی کردیم. ولی دوباره نکات بالا را باهم بررسی می کنیم.

1.       رفتار یک شی توسط حالت داخلی آن شی مشخصی می شود که در مقابل رخ دادن یک رویداد می تواند تغییر کند.

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

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

  

 

کلاس Context کلاسی است که می تواند دارای چندین حالت داخلی باشد در مثال ما همان Media Player.

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

کلاس های Concrete، عمل های را که شی در آن حالت انجام می دهد، پیاده سازی می کنند.(کلاسهای PlayState, StopState,PauseState)

 

نیایش


ای‌ خداوند!

به‌ علمای‌ ما مسوولیت                                                                                   

و به‌ عوام‌ ما علم‌ و به دینداران ما دین  

و  به‌ مومنان‌ ما روشنایی‌ و به‌ روشنفکران‌ ما ایمان‌

و به‌ متعصبین‌ ما فهم‌ و به‌ فهمیدگان‌ ما تعصب

و به‌ زنان‌ ما شعور و به‌ مردان‌ ما شرف‌

 و به‌ پیران‌ ما آگاهی‌ و به‌ جوانان‌ ما اصالت

‌و به‌ اساتید ما عقیده‌ و به‌ دانشجویان‌ ما نیز عقیده

و به‌ خفتگان‌ ما بیداری‌ و به‌ بیداران‌ ما اراده 

و به نشستگان ما قیام‌ و به‌ خاموشان‌ ما فریاد

 و به‌ نویسندگان‌ ما تعهد و به‌ هنرمندان‌ ما درد و به‌ شاعران‌ ما شعور

و به‌ محققان‌ ما هدف‌ و به مبلغان ما حقیقت 

و به‌ حسودان‌ ما شفا و به‌ خودبینان‌ ما انصاف‌

و به‌ فحاشان‌ ما ادب‌

و به‌ فرقه‌های‌ ما وحدت‌

و به مردم ما خود آگاهی

و به‌ همه‌ ملت‌ ما همت‌ تصمیم‌ و استعداد فداکاری‌ و شایستگی‌ نجات‌ و عزت‌ ببخشا.

خدایا: خودخواهی را چندان در من بکُش ، یا چندان برکش

تا خودخواهی دیگران را احساس نکنم و از آن در رنج نباشم.

 خدایا: به مذهبی ها بفهمان که:

آدم از خاک است.

بگو که:

یک پدیده مادی نیز به همان اندازه خدا را معنی می کند که یک پدیده غیبی،

در دنیا همان اندازه خدا وجود دارد که در آخرت.

و مذهب اگر پیش از مرگ به کار نیاید ، پس از مرگ به هیچ کار نخواهد آمد.

دکتر شریعتی

سر فصل و منابع درس مهندسی نرم افزار

سرفصل و منابعی که توسط وزارت علوم برای درس مهندسی نرم افزار 1 و 2 در نظر گرفته شده است.

 

مهندسی نرم افزار 1

سر فصل مطالب

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

مفاهیم تحلیل سیستم ها، سیستم های اطلاعاتی ساختیافته، مدل فیزیکی جریان داده های سیستم موجود، مدل منطقی جریان داده های سیستم های پیشنهادی، مدل فیزیکی جریان داده های سیستم های پیشنهادی، مشخصات دقیق خواسته ها، مشخصات فیزیکی داده ها، امکان سنجی سیستم ها با توجه به سه مولفه تکنولوژی – نیروی انسانی و منابع مالی و زمانی، تهیه گزارش امکان سنجی، نمونه سازی، طراحی کلی سیستم شامل طراحی فایل ها یا بانکهای اطلاعاتی، طراحی فرمهای ورودی و گزارشات نهائی، طراحی واسط کاربر، طراحی ساختمان نرم افزار، تعیین مشخصات پردازشها یا عملیات سیستم، تعیین مشخصات فرهنگ داده ها، تهیه گزارش طراحی کلی سیستم.

معرفی روشهای جمع آوری اطلاعات، معرفی روشهای تخمین هزینه و برآورد زمان جهت انجام هر یک از مراحل سیستم، معرفی روشها و ابزار مدیریت پروژه، معرفی ابزار های کمک به تحلیل سیستم، معرفی ابزارهای کمک به طراحی سیستم، معرفی بخش اول CASE

مراجع

1.       Bentley, Barlow and Toppan, System Analysis and Design Methods, 199.

2.       Yourdon, Modern Structured Analysis, Perntice-Hall, 1989.

3.       Fitsgerald and A. Fitzgerald, Fundamentals of System Analysis, 3rd Edition, John Wiley, 1987.

4.       Hawryszkiewgcz, Introduction to System Analysis and Design, 2nd Edition, Prentice-Hall, 1992.

5.       E.M.Awad, System Analysis and Design, 2nd Edition 1985.

6.        K.E.Kendall and J.E. Kendall, Systems Analysis and Design, 2nd Edition, Prentice-Hall, 1992.

7.       B. Boehm, Software Engineering, 4th Edition, Addison-Wesley, 1996.

8.       A. Sommerville, Software Engineering, 4th Edition, Addison-Wesley, 1996.

9.        R. S. Pressman, Software Engineering, A Practitioners Approach, 4th Edition, Mc Graw Hill, 1996.

 

مهندسی نرم افزار 2

سر فصل مطالب

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

مراجع

1.       A. Sommerville, Software Engineering, 4th Edition, Addison-Wesley, 1996.

2.       R. S. Pressman, Software Engineering, A Practitioners Approach, 4th Edition, Mc Graw Hill, 1996.

3.       D. Bell, I. Morrey and J. Pavgh, Software Engineering, A Practical Approach, Prentice-Hall, 1992.

4.       I. Jacobson, Object-Oriented Software Engineering, John Wiley, 1993. 

 

برای یک دوست

مسیح هر چه می گوید تجربه ی خود است ویک مسیحی هر چه می گوید باور اوست. وفاصله ی بین تجربه و باور از زمین تا آسمان است .آن دو هرگز به هم نمی رسند.

اگر می خواهی حقیقت را بشناسی، هیچ گاه باور نکن. نمی گویم که یک بی اعتقاد شو، زیر این نیز یک باور است. یک باور منفی، یک ضد باور …

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

اگر تو به دست یک هندو پرورش یافته باشی، یک هندو خواهی شد و اگر به دست یک مسیحی، یک مسیحی. پس پای شرطی شدن و تعلیم و تربیت در میان است، این که چه کسی معلم تو بود و تو به طور تصادفی در چه محیطی به دنیا آمده ای.آن ها ذهن تو را شرطی کرده اند، ذهن آن ها به دست والدین شان شرطی شده بود و الی آخر.

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

و روزی که خودت تجربه کنی یک مسیح می شوی. برای خودت یک بودا می شوی و این بسیار زیبا است.

یک مسیح بودن زیبا است اما یک مسیحی بودن نه.

اشو

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

(ایام محرم) ، همه حسین را باور دارند، ولی کسی از ما می تواند بار دیگر در شرایط مشابه حسین بودن را تجربه کند. من که ….

حسین باشیم نه حسینی.