توخالی


محدودیت زمان: ۰.۵ ثانیه

محدودیت حافظه: ۱ مگابایت


عدد فرد n در ورودی داده می‎‌شود و شما باید یک لوزی توخالی با استفاده از کاراکتر ستاره * و با قطر n در خروجی چاپ کنید. 1<n<1011< n < 101

ورودی نمونه🔗

9
Plain text

خروجی نمونه🔗

***********
***** *****
****   ****
***     ***
**       **
*         *
**       **
***     ***
****   ****
***** *****
***********
Plain text

آنچه باید آپلود کنید:🔗

فقط یک فایل java. محتوی برنامه‌‎تان را ارسال کنید. توجه داشته باشید که برنامه‎ شما در هیچ بسته (package)ای قرار نداشته باشد.

ساده‌سازی مارک‌دان


یکی از زبان‌های نشانه‌گذاری و قالب‌بندی متن، markdown است.

یاد گرفتن این زبان ساده ‌است و استفاده از آن ساده‌تر! حتی با یک ادیتور متنی ساده هم می‌توان متنی در این قالب نوشت.

همچنین جالب است بدانید متن این سوال نیز در قالب markdown نوشته شده که در نهایت شما آن را به شکل فعلی می‌بینید.

برای آشنایی بیشتر با مارک‌داون می‌توانید از این سایت استفاده کنید.

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

barkhi emkanat e markdown🔗

  • matn e bold shode
  • matn e italic
  • link ke shamel e ebarat e link shode va khode link ast.
  • tekke code be shekl e in yek code ast
  • mored bandi (bullet)
  • in yek tasvir ast.

حالا برای اینکه با قالب مارک‌داون آشنا شوید، قسمتی از متن همین سوال را در زیر می‌بینیم:

### barkhi emkanat e markdown
+ matn e **bold** shode
+ matn e *italic*
+ [link](https://google.com) ke shamel e ebarat e link shode va khode link ast.
+ tekke code be shekl e `in yek code ast`
+ mored bandi (bullet)
+ in yek ![tasvir](https://quera.ir/qbox/view/TtRF7rH95i/pc.png) ast.
Plain text

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

barkhi emkanat e markdown
matn e bold shode
matn e italic
link ke shamel e ebarat e link shode va khode link ast.
tekke code be shekl e
mored bandi (bullet)
in yek tasvir ast.
Plain text

توجه🔗

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

توضیحات حل🔗

  • بسته src را از اینجا دانلود کنید.
  • فایل MarkdownSimpler.java را باز کرده و تکمیل کنید.
  • دقت کنید که ورودی سازنده کلاس ما، یک شی از نوع java.io.File است که به یک فایل متنی اشاره دارد. محتوای آن فایل متنی، همان ورودی ما در قالب markdown است.

    آنچه باید آپلود کنید:🔗

    پس از حل سوال و پیاده‌سازی متد خواسته‌شده، فقط همان فایل MarkdownSimpler.java را آپلود کنید. در اسم فایل و کلاس‌ و متد‌های موجود هیچ تغییری ندهید.

کنترل تلویزیون


کنترل تلویزیون احمد پس از قطعی‌های پی‌درپی برق ناگهان از کار افتاد و هیچ دکمه‌ای کار نمی‌کرد.

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

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

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

به او کمک کنید کلاس‌های مربوط به کنترل تلویزیون را به گونه‌ای ایجاد و پیاده‌سازی کند که همه‌ تست‌ها پاس شوند و کنترل بتواند مثل قبل کار کند.

  • دانلود تست‌های احمد
    • برای اجرای تست‌ها نیاز به کتاب‌خانه JUnit دارید. برای راحتی بیشتر، یک نسخه از این کتاب‌خانه را در کنار تست‌ها قرار داده‌ایم و در صورت نیاز می‌توانید از آن استفاده کنید.

آنچه باید آپلود کنید🔗

یک فایل زیپ آپلود کنید که در آن بسته ir.mci.tv به صورت زیر وجود داشته باشد:

.
└── ir
    └── mci
        └── tv
            └── *.java
            ...
Plain text

به صورتی که وقتی فایل زیپ را باز می‌کنیم، دقیقا شاخه‌ ir را ببینیم که درون آن شاخه mci و درون آن نیز شاخه tv قرار دارد. در داخل tv فایل‌هایی که ایجاد و پیاده‌سازی کرده‌اید باید قرار داشته باشد.

مخاطبین پردردسر


محدودیت زمان: ۱ ثانیه

محدودیت حافظه: ۲۵۶ مگابایت


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

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

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

ورودی🔗

ورودی شامل خطوط زیادی است که در هر خط مشخصات یک مخاطب با ترتیب: نام، نام خانوادگی و شماره تلفن داده می‌شود. در آخرین خط کلمه end می‌آید که نشان‌دهنده پایان لیست مخاطبین است.

خروجی🔗

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

نکات🔗

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

مثال🔗

ورودی نمونه 1🔗

Anny Ancell 07855941290
Bert Correy 07935869924
Alice Chandler 07855941290
Alexina Bradly 07916430053
Bert Antony 07082369342
Augustine Chandler 07056462105
end
Plain text

خروجی نمونه 1🔗

4
2
Plain text

توضیح:🔗

با توجه به ورودی، چهار دسته خواهیم داشت:

  • یک دسته شامل Bert Correy و Bert Antony
  • یک دسته شامل Alice Chandler و Augustine Chandler
  • یک دسته شامل Anny Ancell
  • یک دسته شامل Alexina Bradly و اندازه بزرگترین دسته هم 2 است.

ورودی نمونه 2🔗

Anny Ancell 07855941290
Bert Correy 07935869924
Alice Chandler 07855941290
Alexina Bradly 07916430053
Benedicta Bail 07078776472
Adi Chicky 07972273430 
Adey Amery 07942539378
Christalle Dale 07916430053
end
Plain text

خروجی نمونه 2🔗

8
1
Plain text

توضیح:🔗

هیچ دو نفری نام یا نام خانوادگی یکسان ندارند و هر فرد در یک دسته مجزا قرار می‌گیرد.

ورودی نمونه 3🔗

Anny Ancell 07855941290
Bert Ancell 07935869924
Anny Chandler 07855941290
Bert Bradly 07916430053
Anny Bail 07078776472
Adi Chicky 07972273430 
Adey Bail 07942539378
Adi Bail 07916430053
end
Plain text

خروجی نمونه 3🔗

1
8
Plain text

توضیح:🔗

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

توجه کنید که همه افرادی که در یک دسته قرار می‌گیرند، لزوما دو به دو نام یا نام خانوادگی یکسان ندارند. مثلا Anny Ancell و Bert Bradly نام و نام خانوادگی یکسان ندارند اما با Bert Ancell شباهت دارند و به همین دلیل همگی در یک دسته قرار می‌گیرند.

آنچه باید آپلود کنید:🔗

کافی است یک فایل .java شامل پیاده‌سازی خود را بدون نیاز به زیپ کردن، ارسال کنید.

موازی‌کاری


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

فایل Source را دانلود کرده و محتوای آن را ببینید. شما باید متد solve از کلاس Parallelism را مطابق با توضیحات زیر پیاده‌سازی کنید.

شما باید پردازش این درخت را از پایین‌ترین سطح (برگ‌ها) شروع کرده و به بالاترین سطح که ریشه درخت در آن قرار دارد برسید. هر Node درخت، دارای سه ویژگی اندیس و پدر و تابع است.

  • اندیس (index): اندیس نود را تعیین می‌کند. نودهای موجود در هر سطح، یک اندیس یکتا دارند.
  • پدر (parent): نود پدر را تعیین می‌کند. برای نود ریشه مقدار آن null است.
  • تابع (func): تابع نود را تعیین می‌کند. برای پردازش هر نود این تابع باید فراخوانی شود.

پردازش درخت باید به این صورت باشد که:

  1. نودهای هر سطح از درخت به صورت موازی و همزمان با هم پردازش شوند (متد funcشان اجرا شود)
  2. فقط زمانی که کار پردازش نودهای یک سطح تمام شد، پردازش نودهای سطح بالاتر می‌تواند آغاز شود.
  3. در هر سطح از درخت، هر نود باید با یک ترد هم‌نام با اندیسش پردازش شود.

نکته🔗

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

مثال🔗

با اجرای متد main از کلاس Main خروجی زیر یکی خروجی‌‎های صحیح محتمل است.

D1 by 1 - F1 by 1 - F2 by 2 - G1 by 1 - G2 by 2 - H1 by 1 -  
Plain text

درختی که در این مثال داده شده است، چنین ساختاری دارد:

.
└── H1
    ├── G1
    ├── G2
        ├── F1
               ├── D1
        ├── F2
Plain text

توجه داشته باشید که تمامی Dها قبل از Fها و تمامی Fها قبل از Gها و تمامی Gها قبل از Hها چاپ شده‌اند. هم‌چنین هر نود توسط ترد هم‌نام با اندیسش پردازش شده است.

آنچه باید آپلود کنید🔗

یک فایل زیپ آپلود کنید که در آن بسته ir.mci.parallel به صورت زیر وجود داشته باشد:

.
└── ir
    └── mci
        └── parallel
            └── Parallelism.java
Plain text

به صورتی که وقتی فایل زیپ را باز می‌کنیم، دقیقا شاخه‌ ir را ببینیم که درون آن شاخه mci و درون آن نیز شاخه parallel قرار دارد. در داخل parallel فایل‌ Parallelism.java باید قرار داشته باشد.

چشمک


شما قرار است بخشی از بازی چشمک را پیاده‎‌سازی کنید. در این نسخه از بازی قوانین زیر وجود دارد.

  • در ابتدای بازی، کارت‎‌ها بین بازیکن‌‎ها توزیع می‌‎شود. روی یکی از کارت‌ها علامت (چشمک) قرار دارد.
  • بازیکنی که کارت چشمک دارد (چشمک‎‌زن)، در هر مرحله از بازی می‌‎تواند به یک یا چند بازیکن دیگر چشمک بزند.
  • با دریافت چشمک توسط یک بازیکن، آن بازیکن می‎‌میرد (حذف می‌‎شود).
  • هر بازیکن می‎‌تواند حدس بزند، چه کسی چشمک‌‎زن است:
    • اگر حدس وی درست باشد، برنده شده و بازی تمام می‌‎شود؛
    • وگرنه، می‎‌میرد (حذف می‎‌شود).
  • اگر در بازی، حداکثر دو نفر باقی بمانند، بازی تمام شده و چشمک‌‎زن پیروز می‌‎شود.

فایل Source را دانلود کرده، وارد بسته ir.mci.wink شده و محتوای آن را ببینید:

توضیحات:🔗

  • واسط WinkGame: این واسط را باید پیاده‌‎سازی کنید (در کلاس WinkGameImpl).
  • واسط Dealer: یک متد deal() دارد که به هر یک از بازیکن‌‎ها، یک کارت تخصیص می‌‎دهد که تنها یکی از آن‌‎ها علامت چشمک دارد. این واسط توسط ما پیاده‎‌سازی می‌‎شود.
  • کلاس Card: نشان‌دهنده کارتی است که بین بازیکن‎‌ها پخش می‎‌شود.
  • واسط PlayerState: واسطی شامل متدهایی برای دریافت وضعیت و انتقال وضعیت بازیکن است. این واسط یک متد state() دارد که وضعیت فعلی بازیکن را در قالب یک enum (از نوع PlayerState.State) بر می‎‌گرداند.
  • واسط Player: از واسط PlayerState ارث‌‎بری می‌‎کند. هر شی که به عنوان بازیکن در برنامه وجود دارد از نوع Player است. این واسط نیز توسط ما پیاده‎‌سازی می‎‌شود.

نمودار وضعیت بازیکن:🔗

شکل زیر، نمودار وضعیت بازیکن را نشان می‎‌دهد. با فراخوانی هر یک از متدها روی شیِ بازیکن، انتقال وضعیت انجام می‎‌شود. وضعیت‌‎ها در واقع همان مقادیر PlayerState.State هستند که توسط متد state() از بازیکن قابل دریافت هستند.

نمودار وضعیت

مثال:🔗

در بسته ir.mci.wink.example، یک پیاده‎‌سازی ساده از Player و Dealer وجود دارد که در متد main از کلاس Main استفاده شده است. با پیاده‌‎سازی صحیح WinkGameImpl و با اجرای برنامه، خروجی زیر به دست می‌‎آید:

Round #1:
[Player[id=100, state=PLAYING], Player[id=300, state=PLAYING], Player[id=500, state=PLAYING], Player[id=600, state=ELIMINATED]]

Round #2:
Winner: Player[id=500, state=WON]
[Player[id=100, state=FINISHED], Player[id=300, state=ELIMINATED], Player[id=500, state=WON], Player[id=600, state=ELIMINATED]]
Plain text

باید توجه داشت که در تست‎‌ها از پیاده‌‎سازی پیشرفته‌‎ترِ Player استفاده می‌‎شود. در این پیاده‌‎سازی در فراخوانی متدها، وضعیت فعلی بازیکن چک می‌‎شود و در صورتی که طبق نمودار وضعیت نبود، خطای IllegalStateException پرتاب می‌‎شود. این نکته در مورد پیاده‎‌سازی Dealer نیز صدق می‎‌کند.

متدهای WinkGame:🔗

  • متد join(Player): بازیکن ورودی را به بازی ملحق می‎‌کند و متد onJoin این بازیکن را فراخوانی می‎‌کند.
  • متد prepare(): پس از فراخوانی این متد، دیگر بازیکنی نمی‌‎تواند به بازی ملحق شود. همچنین متد onPrepare برای تمامی بازیکن‎‌ها فراخوانی می‎‌شود.
  • متد dealing(): در این متد، به کمک شیِ dealer، کارت‎‌ها بین بازیکن‎‌ها توزیع می‌‎شود و بازیکنِ چشمک‎‌زن را بر می‌‎گرداند. برای تحویل کارت به هر بازیکن، باید متد onDeal(Card) وی فراخوانی شود.
  • متد playRound(): یک مرحله از بازی را انجام می‌‎دهد و در صورتی که برنده بازی مشخص شود، وی را برمی‌‎گرداند:
    • ابتدا باید روی تمامیِ بازیکن‎‌های در حال بازی (دارای وضعیت Playing)، متد playRound(List<Player>) فراخوانی شود. ورودیِ این متد باید بازیکن‎‌های در حال بازی (به جز خود بازیکن) باشد.
    • با فراخوانی متد detectedWinker() از بازیکن‎‌ها (به غیر از چشمک‎‌زن)، بازیکن چشمک‌‎زن را (در صورت تشخیص) برمی‎‌گرداند؛ اگر تشخیص بازیکنی درست بود: متد onWin() روی وی، متد onDetected() روی چشمک‌‎زن و متد onFinished() روی سایر بازیکن‎‌ها فراخوانی می‎‌شود. بازیکن تشخیص‌‎دهنده به عنوان برنده برگردانده می‌‎شود. اگر تشخیص بازیکن اشتباه بود: متد onWrongDetection() روی وی فراخوانی می‎‌شود.
    • با فراخوانی متد winkedPlayers() از بازیکنِ چشمک‎‌زن، بازیکن‌‎هایی که چشمک خورده‎‌اند برگردانده می‎‌شود و روی این بازیکن‎‌ها، متد onWink() صدا زده می‌‎شود.
    • اگر حداکثر دو بازیکن باقی‌مانده باشند، چشمک‎‌زن برنده می‌‎شود و متد onWin() روی آن صدا زده می‌‎شود و به عنوان برنده برگردانده می‎‌شود. هم‌چنین روی بازیکن باقی‌‎مانده نیز متد onFinished() صدا زده می‎‌شود.

نکات و راهنمایی🔗

  • در هر دور حداکثر یک نفر چشمک‌زن را درست تشخیص می‎‌دهد و یا به عبارت دیگر، بازی حداکثر یک برنده دارد.
  • متدهایی که خروجی Optional دارند هیچ‎گاه نباید null برگردانند، بلکه باید یک Optional خالی برگردانند.
  • در فراخوانی متدها روی هر بازیکن دقت کنید و وضعیت بازیکن را در نظر بگیرید. برای مثال روی بازیکن حذف‎‌شده (وضعیت Eliminated) نمی‎‌توان متد onWink را صدا زد.

آنچه باید آپلود کنید:🔗

یک فایل زیپ آپلود کنید که در آن بسته ir.mci.wink.impl به صورت زیر وجود داشته باشد:

.
└── ir
    └── mci
        └── wink
            └── impl
                └── WinkGameImpl.java
Plain text

به صورتی که وقتی فایل زیپ را باز می‌کنیم، دقیقا شاخه‌ ir را ببینیم که درون آن شاخه mci و درون آن شاخه wink و درون آن نیز شاخه impl قرار دارد. در داخل شاخه impl، فقط و فقط فایل WinkGameImpl.java وجود دارد.