برای استفاده از تمام امکانات سایت از جمله مرکز دانلود باید در سایت عضو شوید. برای ثبت نام تنها 1 دقیقه زمان نیاز دارید ، برای ثبت نام اینجا کلیک کنید

صفحه اول انجمنها
ثبت نامجستجوراهنماي انجمنليست اعضااتاق چت (0)گروه هاي كاربرانمرکز دانلودورود

پاسخ به يك موضوع صفحه 5 از 7
برو به صفحه قبلي  1, 2, 3, 4, 5, 6, 7  بعدي
بررسی سوالات ACM_ICPC ( فعلا شریف 2001)
نويسنده پيغام

پاسخ بصورت نقل قول
ارسال problem e: a old stone game 
واقعا سوال وحشتناکی بود . یه روز روش وقت گذاشتم.

امیدوارم مفید باشه !


_________________
آگه 50000 نفر هم به یک چیز اشتباه اعتقاد داشته باشن , اون چیز هنوز هم اشتباه است !

محمـــــــــــــــــــــدرضا . اگر گه گاهی سراغتون افتاد , خوشحال میشم : http://360.yahoo.com/molla652003

سوابق کاریه من :

معاد
روزی یک حدیث
ACM_sharif
طراحی الگوریتم
در اعماق بی کران
Art Of Programming
عکس های بچه ها
نماز
معرفی سایت های مفید
شعر های دوران مهدکودک
موفقیت
موسیقی

پاسخ بصورت نقل قول
ارسال  
یه روش دیگه هم برای سوال بالا به نظرم رسید که فکر کنم کدش کمتر بشه , شاید ساده تر هم بشه :

باید اول درخت رو به هر روشی که می تونید درست کنید . بعد یه پیمایش level order از پایین به بالا لازم داره (یعنی از برگ ها به سمت ریشه ) , اون هم به شکلی که شما تو هر level , اول تو اون برادر هایی سنگ بزارین که ماکزیمم اند . یعنی مثلا اگه ریشه 2 تا child داشته باشه و یکی 5 تا و اون یکی 6 تا بچه داشته باشن , اول باید تو 6 تا سنگ بزارین , بعد تو 5 تا. و به همین ترتیب بیاین بالا . و ماکزیمم سنگ های لازم رو حساب کنید.

حالا کد نویسی اش با خودتون !


_________________
آگه 50000 نفر هم به یک چیز اشتباه اعتقاد داشته باشن , اون چیز هنوز هم اشتباه است !

محمـــــــــــــــــــــدرضا . اگر گه گاهی سراغتون افتاد , خوشحال میشم : http://360.yahoo.com/molla652003

سوابق کاریه من :

معاد
روزی یک حدیث
ACM_sharif
طراحی الگوریتم
در اعماق بی کران
Art Of Programming
عکس های بچه ها
نماز
معرفی سایت های مفید
شعر های دوران مهدکودک
موفقیت
موسیقی

پاسخ بصورت نقل قول
ارسال PROBLEM D: counting rectangles 
فكر كنم اين كد مشكلات كد قبلي رو نداشته باشه
code:

#include <iostream>
#include <fstream>
#include"stdio.h"
using namespace std;
int main()
{
   struct
   {
      int x1,x2,y1,y2;
   }y[100],x[100],temp;
   int ix=0,jy=0,i,j,tx1,tx2,ty1,ty2,m,s,k,l,cnt;
   FILE *in=fopen("d.in","r");
   fscanf(in,"%d",&m);
   for(;m;--m)
   {
      cnt=0;
      ix=jy=0;
      fscanf(in,"%d",&s);
      for(;s;--s)
      {
         fscanf(in,"%d %d %d %d",&tx1,&ty1,&tx2,&ty2);
         if(tx1==tx2)
         {
            if(ty1>ty2)
            {
               l=ty1;
               ty1=ty2;
               ty2=l;
            }
            y[jy].y1=ty1;y[jy].y2=ty2;
            y[jy].x1=tx2;y[jy].x2=tx2;
            jy++;
         }
         else
         {
            if(tx1>tx2)
            {
               l=tx1;
               tx1=tx2;
               tx2=l;
            }
            x[ix].x1=tx1;x[ix].x2=tx2;
            x[ix].y1=ty1;x[ix].y2=ty2;
            ix++;
         }
      }
      for(i=0;i<ix;i++)
         for(j=0;j<ix;j++)
            if(x[i].y1<x[j].y1)
            {   
               temp=x[i];
               x[i]=x[j];
               x[j]=temp;
            }
      for(i=0;i<jy;i++)
         for(j=0;j<jy;j++)
            if(y[i].x1<y[j].x1)
            {
               temp=y[i];
               y[i]=y[j];
               y[j]=temp;
            }
      for(i=0;i<jy;i++)
         for(j=0;j<ix;j++)
            if(y[i].x1>=x[j].x1&&y[i].x1<=x[j].x2&&y[i].y1<=x[j].y1&&y[i].y2>=x[j].y1)
               for(k=j+1;k<ix;k++)
                  if(y[i].x1>=x[k].x1&&y[i].x1<=x[k].x2&&y[i].y1<=x[k].y1&&y[i].y2>=x[k].y1)
                     for(l=i+1;l<jy;l++)
                        if(y[l].x1>=x[j].x1&&y[l].x1<=x[j].x2&&y[l].y1<=x[j].y1&&y[l].y2>=x[j].y1&&y[l].x1>=x[k].x1&&y[l].x1<=x[k].x2&&y[l].y1<=x[k].y1&&y[l].y2>=x[k].y1)
                           cnt++;
   cout<<cnt<<"\n";
   }

}



پاسخ بصورت نقل قول
ارسال F:magazine delivery 
احسان جان خیلی ممنون.

کدم رو تا حدودی تصحیح کردم.

کسی می دونه time limit این سوال چقده ؟ کد من تو حدود 14 ثانیه جواب میده.

مشکل از sort کردنش بود. و استفاده از تابع کند unique !!

code:
#include <iostream>
#include <fstream>
#include <vector>
#include <algorithm>
#include <list>
const int _invalid=1000000000;
using namespace std;
struct now{
   int a,b,c,sum;
   now(int aa,int bb, int cc,int ss){
      a=aa;
      b=bb;
      c=cc;
      sum=ss;
   }
   bool operator == (now & p) const {
      return (a==p.a && b==p.b && c==p.c /*&& sum==p.sum*/ );
   }
};
vector<vector<now> > paths;
vector <vector <int> > cost;
void sorting (now & p){
   if (p.a<p.b)
      swap (p.a,p.b);
   if (p.a<p.c)
      swap(p.a,p.c);
   if (p.b<p.c)
      swap(p.b,p.c);
}
bool cmd (now &p,now &q) {
   if (p.a!=q.a)
      return p.a<q.a;
   else if (p.b!=q.b)
      return p.b<q.b;
   else if (p.c!=q.c)
      return p.c<q.c;
   else
      return p.sum < q.sum;
}
int main(){
   ifstream in("sharif_99_F.in");
   int t,n;
   for (in >> t;t>0;--t){
      in>>n;
      cost.assign ( n ,vector <int> (n));
      for (int i=0;i<n-1;++i)
         for(int j=i+1;j<n;++j)
            in >> cost[i][j];

      paths.assign(n ,vector<now>());
      now home(0,0,0,0);
      paths[0].push_back(home);
      for (int i=1;i<n;++i){
         for (size_t j=0;j<paths[i-1].size();++j){
            int a,b,c,each_cost;
            for (int l=0;l<3;++l){
               switch (l) {
                  case 0:a=i,b=paths[i-1][j].b,c=paths[i-1][j].c;
                     each_cost=cost[paths[i-1][j].a][i];
                     break;
                  case 1:b=i,a=paths[i-1][j].a,c=paths[i-1][j].c;
                     each_cost=cost[paths[i-1][j].b][i];
                     break;
                  case 2:c=i,b=paths[i-1][j].b,a=paths[i-1][j].a;
                     each_cost=cost[paths[i-1][j].c][i];
                     break;
               }
               now point(a,b,c,paths[i-1][j].sum + each_cost);
               sorting(point);
               paths[i].push_back(point);
            }
            sort (paths[i].begin(),paths[i].end(),cmd);
            for (size_t r=0;r<paths[i].size()-1;++r)
               if (paths[i][r]==paths[i][r+1])
                  paths[i].erase(paths[i].begin()+r+1);
               //for (size_t j=r+1 ;j<paths[i].size();++j)
               //   if ( paths[i][r]==paths[i][j] ){
               //      int p=paths[i][r].sum > paths[i][j].sum ? r : j;
               //      paths[i].erase(paths[i].begin()+p);
               //      //--r;
               //      break;
               //   }

         }
      }
      int minimum=_invalid;
      for (size_t i=0;i<paths[n-1].size();++i)
         minimum = min (paths[n-1][i].sum , minimum);
      cout << minimum << endl;
         
   }
   return 0;
}



_________________
آگه 50000 نفر هم به یک چیز اشتباه اعتقاد داشته باشن , اون چیز هنوز هم اشتباه است !

محمـــــــــــــــــــــدرضا . اگر گه گاهی سراغتون افتاد , خوشحال میشم : http://360.yahoo.com/molla652003

سوابق کاریه من :

معاد
روزی یک حدیث
ACM_sharif
طراحی الگوریتم
در اعماق بی کران
Art Of Programming
عکس های بچه ها
نماز
معرفی سایت های مفید
شعر های دوران مهدکودک
موفقیت
موسیقی

پاسخ بصورت نقل قول
ارسال  
سلام.
سئوالهای شریف معمولا time limit شون در حدود 20 یا 30 ثانیه است. پس راه حل شما اگه درست کار میکنه از نظر زمان مشکلی نداره.

یک راه خیلی خوب و آسون هم وجود داره. میشه به صورت بازگشتی بنویسیدش. یعنی اینطوری:
برای هر نود دو تا عدد مشخص میکنید:
  n1: تعداد فرزندان اون نود بعلاوه یک
  n2: ماکزیمم تعدادی که هر فرزند اون نود سنگ لازم داره (که خود سنگهای مورد نیاز هر فرزند بازگشتیه)
بعد بین n1 و n2 ماکزیمم میگیریم.
اگر هم نودی فرزند نداشت، خود به خود مقدار یک رو به عنوان جواب برمیگردونه و حالت خاصی لازم نیست چک بشه (چون تعداد فرزنداش بعلاوه یک میشه یک)
جواب میشه تعداد سنگهای لازم برای ریشه.

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


پاسخ بصورت نقل قول
ارسال  
بازگشتي چه جوري ؟ ايني که ميگين بايد به هر نود که مي رسيم قبلش فرزند هاش چک شده باشن . و خوب مسلما بايد سطح به سطح بيايم  بالا تا به ريشه برسيم . چه جوري بايد با اين نوع درخت level order رو بازگشتي بنويسم ؟

يه جورايي نوشتم ولي غلط جواب داد:

code:
int toloo(node *p){
   int temp1=0,temp2=0;
   if (p->down)
      temp1=toloo(p->down);
   if (p->right)
      temp2=toloo(p->right);
   return max(p->num_childs+1,max(temp1,temp2));
}



_________________
آگه 50000 نفر هم به یک چیز اشتباه اعتقاد داشته باشن , اون چیز هنوز هم اشتباه است !

محمـــــــــــــــــــــدرضا . اگر گه گاهی سراغتون افتاد , خوشحال میشم : http://360.yahoo.com/molla652003

سوابق کاریه من :

معاد
روزی یک حدیث
ACM_sharif
طراحی الگوریتم
در اعماق بی کران
Art Of Programming
عکس های بچه ها
نماز
معرفی سایت های مفید
شعر های دوران مهدکودک
موفقیت
موسیقی

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


پاسخ بصورت نقل قول
ارسال  
سلام.
ببخشین دیر شد، زود تر فرصت نکردم.
code:
#include <iostream>
#include <cmath>
#include <fstream>
#include <map>
#include <vector>

using namespace std;

ifstream fin ("e.in");
vector <vector<int> > v;

void readCase()
{
   v.clear();

   int N;
   fin >> N;
   v.resize(N + 1);
   while (N--)
   {
      int label, r;
      fin >> label >> r;
      v[label].resize(r);
      for (int i = 0 ; i <r>> v[label][i];
   }
}

int calculateNeededStones (int parent)
{
   int temp1 = 0,   //maximum stones needed for childs
      temp1Cnt=0 ,//number of childs which need maximum stones
      temp2;      //number of children
   for (int i = 0; i < v[parent].size(); i++)
      temp1 = max(temp1, calculateNeededStones(v[parent][i]));

   for (int i = 0; i <v>> T;
   while (T--)
   {
      readCase();   //read the input for one test case in a 2d vector
      cout << calculateNeededStones(1) << endl;
   }
   return 0;
}


راستی تو توضیحش یک اشتباهی کرده بودم. چون این و خیلی وقت پیش حل کرده بودم و درست یادم نبود. الان که اومدم بنویسمش دیدم یک جایی رو اشتباه گفتم.
تو قسمت بازگشتی n1 و n2 رو که گفته بودم در مورد n1 اشتباه گفتم. باید ماکزیمم تعداد سنگهای فرزندان یک نود رو بدست بیارین(maxS). بعد n1 میشه تعداد اون فرزندهایی که تعداد سنگهای مورد نیازشون برابر با اون ماکزیممه است.

البته من خروجی رو نداشتم که تست کنم ببینم درسته یا نه. ولی با کد آقای ملایی که مقایسه کردم، با اون کد اولی که فرستاده بودن، جوابهای متفاوت میده! نمیدونم کدومشون اشتباهه!!



اين نامه توسط طلوع در 3 شنبه Aug 07, 2007 10:59 pm ويرايش شده است.

پاسخ بصورت نقل قول
ارسال  
توجه: همه باید وقتی کد می ذارین گزینه ی "دستورات HTML در اين نامه غير فعال شوند" رو تیک بزنید .

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

خروجی اش هم تو سایت شریفگفته بود باید این جوری باشه :

code:
4
5
4
7
4
50
28
10
3



_________________
آگه 50000 نفر هم به یک چیز اشتباه اعتقاد داشته باشن , اون چیز هنوز هم اشتباه است !

محمـــــــــــــــــــــدرضا . اگر گه گاهی سراغتون افتاد , خوشحال میشم : http://360.yahoo.com/molla652003

سوابق کاریه من :

معاد
روزی یک حدیث
ACM_sharif
طراحی الگوریتم
در اعماق بی کران
Art Of Programming
عکس های بچه ها
نماز
معرفی سایت های مفید
شعر های دوران مهدکودک
موفقیت
موسیقی

پاسخ بصورت نقل قول
ارسال  
سلام علیکم!
خوب با توجه به output، دیدم که برنامه ام اشتباه بوده!
الان درستش کردم:
code:
#include <algorithm>
#include <iostream>
#include <cmath>
#include <fstream>
#include <map>
#include <vector>

using namespace std;

ifstream fin ("e.in");
vector <vector<int> > v;

void readCase()
{
   v.clear();

   int N;
   fin >> N;
   v.resize(N + 1);
   while (N--)
   {
      int label, r;
      fin >> label >> r;
      v[label].resize(r);
      for (int i = 0 ; i < r ; i++)
         fin >> v[label][i];
   }
}

int calculateNeededStones (int parent)
{
   if (v[parent].size() == 0) return 1;

   vector <int> stones;

   for (int i = 0; i < v[parent].size(); i++)
      stones.push_back(calculateNeededStones(v[parent][i]));
   sort (stones.begin(), stones.end(), greater<int>());
   
   int pickedStones = stones[0];
   int res = pickedStones;
   for (vector <int>::iterator it = stones.begin(); it != stones.end(); it++)
   {
      if (pickedStones < *it)
      {
         res+= *it- pickedStones;
         pickedStones+= *it - pickedStones;
      }
      pickedStones--;
   }

   return res;
}

int main()
{
   int T;
   fin >> T;
   while (T--)
   {
      readCase();   //read the input for one test case in a 2d vector
      cout << calculateNeededStones(1) << endl;
   }
   return 0;
}

مشکل از اون قسمت اصلی یعنی تابع بازگشتی بود. برای محاسبه تعداد سنگهای مورد نیاز تو هر نود، این کار باید انجام بشه:
تعداد سنگهای لازم برای فرزندان و بدست میاریم (بازگشتی) بعد تو یک آرایه نگهشون میداریم.
آرایه رو نزولی مرتب میکنیم (استفاده از greater برای نوع int در تابع sort)
حالا برابر با خونه اولین این آرایه (بیشترین مقدار فرزندان) سنگ برمیداریم (pickedStones)
بعد یک حلقه روی این ارایه مینویسیم (iterator روی vector مثلا) از بزرگ به کوچک. به هر فرزند یک سنگ از سنگهایی که برداشتیم میدیم. قبلش اگه سنگهایی که برداشتیم از سنگهای مورد نیاز اون فرزند کمتر بود همون مقدار که کمتر بوده به pickedStones و به result اضافه میکنیم.


پاسخ بصورت نقل قول
ارسال  
خیلی ممنون آقا مرتضی , خیلی جالب بود.

از سوال های شریف 99 فقط B و C مونده , رو C یه کم فکر  کنیم ببینیم چی میشه , اگه حل شد که کدش رو می زارم , و گرنه می ریم سراغ 2000 .

موافقین ؟


_________________
آگه 50000 نفر هم به یک چیز اشتباه اعتقاد داشته باشن , اون چیز هنوز هم اشتباه است !

محمـــــــــــــــــــــدرضا . اگر گه گاهی سراغتون افتاد , خوشحال میشم : http://360.yahoo.com/molla652003

سوابق کاریه من :

معاد
روزی یک حدیث
ACM_sharif
طراحی الگوریتم
در اعماق بی کران
Art Of Programming
عکس های بچه ها
نماز
معرفی سایت های مفید
شعر های دوران مهدکودک
موفقیت
موسیقی
نمايش نامه هاي ارسال شده قبلي:
پاسخ به يك موضوع صفحه 5 از 7
برو به صفحه قبلي  1, 2, 3, 4, 5, 6, 7  بعدي