View Full Version : مبتدی: راهنمایی برای نوشتن برنامه ++C
Mohamad15
چهارشنبه 19 مهر 1391, 11:38 صبح
سلام دوستان عزیز
من تازه دوره ++C رو گذروندم و الان برای پروژه پایانی دوره نیاز به یکم راهنمایی دارم.
استاد گفته برنامه ای بنویسید که دو عدد صحیح رو دریافت کنه و بزرگترین رقم مشترک بین اونها رو چاپ کنه!
مثلا بین اعداد 4956 و 6132 بزرگترین رقم مشترک که 6 میشه رو چاپ کنه.
میخواستم اساتید یکم راهنمایی کنن و بگن مکانیزم این برنامه چیه و از چه راهی باید نوشت؟
ممنون
مسعود اقدسی فام
چهارشنبه 19 مهر 1391, 12:52 عصر
۰- یه متعیر موقت مثل a با مقدار 1- تعریف کن
۱- یه حلقه while با شرط عدد 1 تعریف کن. (حلقه بینهایت)
۲- داخل حلقه باقیمانده تقسیم بر ده هر دو عدد رو حساب کن. اگه این باقیماندهها یکی بودن اون رقم رو بریز داخل a
۳- خارج قسمت تقسیم دو عدد بر ده رو بذار جای خودشون. مثلا 434321 بشه 43432
۴- جک کن اگه یکی از این دو عدد جدید صفر بود از حلقه بیا بیرون و گرنه برو به اول حلقه
۵- اگه a همون 1- بود یعنی رقم مشترک ندارن. وگرنه عدد a رو به عنوان نتیجه چاپ کن.
mahak006
چهارشنبه 19 مهر 1391, 13:06 عصر
یه روش ساده اینه که به ترتیب بره عدد اولی باقیمانده به 10 رو بگیری ( رقم یکان ) و بعدش عدد رو تقسیم بر 10 کنی که رقم یکان عوض بشه .
بعدش هر کدوم از رقم هایی که از بالا به دست میاری با کل ارقام عدد دوم مقایسه کنی .عدد دومی هم همونطوری که بالا گفتم رقماشو در بیار ولی خود عدد رو تغییر نده و کپی عدد رو باید تغییر بدی چون به تعداد ارقام عدد اولی ، عدد دومی باید در اختیارت باشه .
حالا هر رقم عدد اول رو که به دست اوردی ، قبل از مقایسه با ارقام عدد دوم ، چک می کنی که آیا رقم انتخابی از بزرگ ترین رقم مشترکی که تا اون مرحله به دست اوردی ، بزرگتر هست یه نه . اگه بود ، میری بره چک کردن با تک تک ارقام عدد دوم و اگه با یکی از ارقام برابر شد ، به عنوان بزرگ ترین رقم مشترک ذخیره میشه . به همین ترتیب تا وقتی که ارقام عدد اول تموم بشه ، تکرار می شه .
mahak006
چهارشنبه 19 مهر 1391, 13:09 عصر
۰- یه متعیر موقت مثل a با مقدار 1- تعریف کن
۱- یه حلقه while با شرط عدد 1 تعریف کن. (حلقه بینهایت)
۲- داخل حلقه باقیمانده تقسیم بر ده هر دو عدد رو حساب کن. اگه این باقیماندهها یکی بودن اون رقم رو بریز داخل a
۳- خارج قسمت تقسیم دو عدد بر ده رو بذار جای خودشون. مثلا 434321 بشه 43432
۴- جک کن اگه یکی از این دو عدد جدید صفر بود از حلقه بیا بیرون و گرنه برو به اول حلقه
۵- اگه a همون 1- بود یعنی رقم مشترک ندارن. وگرنه عدد a رو به عنوان نتیجه چاپ کن.
این الگوریتم اشکالش اینه که دو عدد مثل 8013 و 3568 رو کامل چک نمی کنه . یعنی عدد 8 رو نمی ده بیرون . چون قبلش به 0 می رسه و تموم می شه . البته مشکلات دیگه ای هم داره . اگرم بره الگوریتم بنده اشکالی میبینید ، بگین .
مسعود اقدسی فام
چهارشنبه 19 مهر 1391, 13:11 عصر
این الگوریتم اشکالش اینه که دو عدد مثل 8013 و 3568 رو کامل چک نمی کنه . یعنی عدد 8 رو نمی ده بیرون . چون قبلش به 0 می رسه و تموم می شه .
من گفتم اگه خود عدد خارج قسمت صفر شد، نه باقیمانده. باقیمانده صرفا یکان رو نشون میده. اونجا یکیش خارج قسمت 8 می شه و اونیکی 3.
mahak006
چهارشنبه 19 مهر 1391, 13:24 عصر
من گفتم اگه خود عدد خارج قسمت صفر شد، نه باقیمانده. باقیمانده صرفا یکان رو نشون میده. اونجا یکیش خارج قسمت 8 می شه و اونیکی 3.
پس من اینجا اشتباه کردم . راستی مشکل بعدی اینه که رقم یکان با رقم یکان بررسی می شه و به همین ترتیب . در حالی که برنامه باید یک رقم رو با تک تک ارقام عدد دوم هم بررسی کنه .
Mohamad15
چهارشنبه 19 مهر 1391, 13:24 عصر
جناب ظهیری چیزی که شما گفتید رو زیاد متوجه نشدم!
نفهمیدم چیکار باید بکنم!!
آقای اقدسی فام دلیل اینکه متغیر موقت a=-1 میگیریم دلیلش چیه؟ چرا 1- ؟
مسعود اقدسی فام
چهارشنبه 19 مهر 1391, 13:33 عصر
جناب ظهیری چیزی که شما گفتید رو زیاد متوجه نشدم!
نفهمیدم چیکار باید بکنم!!
آقای اقدسی فام دلیل اینکه متغیر موقت a=-1 میگیریم دلیلش چیه؟ چرا 1- ؟
جون هیچ وقت یه رقم عدد منفی یک نمیشه. پس اگه انتهای الگوریتم a همونطور منفی یک باقی مونده، پس داخل حلقه اصلا مقدارش عوض نشده. یعنی رقم مشترک پیدا نشده. اگه مثلا 9 میذاشتید. آخر حلقه از کجا میفهمیدید این 9 ناشی از عملیات داخل حلقه هست یا همون مقدار اولیه؟
کلا هر عددی غیر از صفر تا نه رو میتونید بذارید. معمولا منفی یک رو به صورت یه سنت قرار میدن. مثلا در الگوریتم جستجو هم اگه عنصر مورد نظر پیدا نشه عدد منفی یک به عنوان محل اندیس در آرایه برگشت داده میشه. اندیس منفی یک که نداریم. پس یعنی عنصری پیدا نشده.
مسعود اقدسی فام
چهارشنبه 19 مهر 1391, 13:35 عصر
پس من اینجا اشتباه کردم . راستی مشکل بعدی اینه که رقم یکان با رقم یکان بررسی می شه و به همین ترتیب . در حالی که برنامه باید یک رقم رو با تک تک ارقام عدد دوم هم بررسی کنه .
آهان. درسته. من مساله رو اشتباه متوجه شده بودم. شرمنده دوست عزیز. اجازه بدید مجددا فکر کنم روی حل مساله.
مسعود اقدسی فام
چهارشنبه 19 مهر 1391, 13:37 عصر
میدونید. بزرگترین رقم مشترک اصولا باید رقم هم ارزش باشه. واسه همین من اون الگوریتم رو گفتم. مثالی که اول تاپیک زدید از خودتون بود یا استاد گفته؟ اگه استاد توضیحی در این مورد نداده بپرسید که چی میشه. ارقام با ارزش یکسان مثلا 454333 و 324151 جواب 4 رو میده. ولو در پنج هم مشترک هستن. الگوریتمی که من گفتم اینطور مساله رو حل می کنه.
mahak006
چهارشنبه 19 مهر 1391, 13:47 عصر
جناب ظهیری چیزی که شما گفتید رو زیاد متوجه نشدم!
نفهمیدم چیکار باید بکنم!!
آقای اقدسی فام دلیل اینکه متغیر موقت a=-1 میگیریم دلیلش چیه؟ چرا 1- ؟
الگوریتم اینه :
a=-1;
while ( x!=0 && y!=0)
{
modx=x%10;
if(modx>a)
for(int i=y;i!=0 && mody!=modx;i/=10)
{
mody=i%10;
if(modx==mody)
a=modx;
}
x=x/10;
mody=-1;
}
بازم اگه جایی از کد اشکالی می بینید ، خوشحال می شم بگید .
Mohamad15
چهارشنبه 19 مهر 1391, 14:37 عصر
این پروژه ایه که استاد داده، دقیقا هم همین چیزی که در پست اول نوشتم رو گفته.
البته استاد گفت 2 تا حلقه while میخواد ولی متوجه نشدم چطوری باید 2تا حلقه while بزنم...
mahak006
چهارشنبه 19 مهر 1391, 14:55 عصر
این پروژه ایه که استاد داده، دقیقا هم همین چیزی که در پست اول نوشتم رو گفته.
البته استاد گفت 2 تا حلقه while میخواد ولی متوجه نشدم چطوری باید 2تا حلقه while بزنم...
خب من که 2 تا حلقه رو برات گذاشتم . فقط یکیش با for نوشتم که اگه بخوای میشه while کردش .
Mohamad15
چهارشنبه 19 مهر 1391, 21:17 عصر
آقای ظهیری این کدی که نوشتید خودتون تست کردید؟ چون من تست کردم جواب نگرفتم!
گام حلقه for درسته؟ مثلا اگه y=83 باشه، بار اول که باقیماندشو میریزه تو mody میشه 3.
بعد که میره تو گام حلقه به نظرم گیر میکنه! میشه یه چک بکنید ببینید چجوریه!اگر درسته که یه توضیحی هم واسه من بدید
ممنون
Mohamad15
چهارشنبه 19 مهر 1391, 22:28 عصر
یه روش ساده اینه که به ترتیب بره عدد اولی باقیمانده به 10 رو بگیری ( رقم یکان ) و بعدش عدد رو تقسیم بر 10 کنی که رقم یکان عوض بشه .
بعدش هر کدوم از رقم هایی که از بالا به دست میاری با کل ارقام عدد دوم مقایسه کنی .عدد دومی هم همونطوری که بالا گفتم رقماشو در بیار ولی خود عدد رو تغییر نده و کپی عدد رو باید تغییر بدی چون به تعداد ارقام عدد اولی ، عدد دومی باید در اختیارت باشه .
حالا هر رقم عدد اول رو که به دست اوردی ، قبل از مقایسه با ارقام عدد دوم ، چک می کنی که آیا رقم انتخابی از بزرگ ترین رقم مشترکی که تا اون مرحله به دست اوردی ، بزرگتر هست یه نه . اگه بود ، میری بره چک کردن با تک تک ارقام عدد دوم و اگه با یکی از ارقام برابر شد ، به عنوان بزرگ ترین رقم مشترک ذخیره میشه . به همین ترتیب تا وقتی که ارقام عدد اول تموم بشه ، تکرار می شه .
اینکه میگید باید ارقامی که از عدد اول بدست میارم با عدد تک تک ارقام عدد دوم مقایسه کنم یعنی چی؟
چجوری باید مقایسه کنم؟ اینجاشو نمیفهمم
مسعود اقدسی فام
چهارشنبه 19 مهر 1391, 22:43 عصر
ببین این جطوره:
int x, y, r1, r2, t, res = -1;
cin >> x >> y;
while( x != 0 )
{
r1 = x % 10;
t = y;
while( t != 0 )
{
r2 = t % 10;
if( r1 == r2 && r1 > res )
{
res = r1;
}
t = t / 10;
}
x = x / 10;
}
cout << res;
اگه رفمی پیدا نشه 1- چاپ میشه. میتونی شرط بذاری که پیام چاپ کنه.
mahak006
چهارشنبه 19 مهر 1391, 23:24 عصر
آقای ظهیری این کدی که نوشتید خودتون تست کردید؟ چون من تست کردم جواب نگرفتم!
گام حلقه for درسته؟ مثلا اگه y=83 باشه، بار اول که باقیماندشو میریزه تو mody میشه 3.
بعد که میره تو گام حلقه به نظرم گیر میکنه! میشه یه چک بکنید ببینید چجوریه!اگر درسته که یه توضیحی هم واسه من بدید
ممنون
اینی که من نوشتم درسته . فقط چون کامل نیست ، به مشکل بر میخوره . تو قبل از اینکه بیای داخل حلقه ها ، mody=-1 بزار . یعنی همون جا که a=-1 گذاشتی . اشکالش همین بود . چون تو شرط حلقه میخواست نابرابری mody با modx رو چک کنه تو استفاده اول از حلقه ، mody بدون مقدار بود .
Mohamad15
پنج شنبه 20 مهر 1391, 11:44 صبح
آقای اقدسی ممنونم...برنامه رو کامل trace کردم و کاملا جواب میده. به نظرم بهینه هم هست.
منطق برنامه رو فهمیدم کاملا...
آقای ظهیری از شما هم ممنونم...
فقط من برنامه رو کامل مینویسم و یکم شاخ و برگ بهش میدم و دوباره اینجا میزارم...
شما لطف کنید یه نگاهی بندازید و نظرتون رو بگید.
lpeiatb
پنج شنبه 20 مهر 1391, 12:47 عصر
سلام، ببخشید اینجا سوالم رو میپرسم
یه سری کد بهمون دادن بنویسیم با c++ 6 که مربوط به درس گرافیک (open GL)
اما وقتی کد ها رو اجرا میکنم همچین اروری میده
Compiling...
Project OpenGL.cpp
c:\program files\microsoft visual studio\myprojects\project opengl\project opengl.cpp(2) : fatal error C1083: Cannot open include file: 'GL/glut.h': No such file or directory
Error executing cl.exe.
به گفته استادمون Open GL نصب نیست، دوستان راهنمایی میکنید چجوری نصب کنم؟
تشکر
vb8334
پنج شنبه 20 مهر 1391, 14:07 عصر
سلام، ببخشید اینجا سوالم رو میپرسم
یه سری کد بهمون دادن بنویسیم با C++ 6 که مربوط به درس گرافیک (open GL)
اما وقتی کد ها رو اجرا میکنم همچین اروری میده
Compiling...
Project OpenGL.cpp
به گفته استادمون Open GL نصب نیست، دوستان راهنمایی میکنید چجوری نصب کنم؟
تشکر
سلام دوست عزیز
شما باید library های opengl رو به visual studio بشناسونی
به اینجا یه سر بزن مشکلت حل میشه:
http://barnamenevis.org/showthread.php?209896-%D8%A2%D9%85%D9%88%D8%B2%D8%B4-OpenGL
http://opengl.blogfa.com/post-16.aspx
http://ins.nafsadh.com/2009/09/07/opengl-and-glut-in-c-with-ms-visual-studio-2008-msvs9/
http://www.cosc.brocku.ca/Offerings/3P98/course/OpenGL/3P98Examples/GettingStarted/msvcnetglut.html
http://user.xmission.com/~nate/glut.html
موفق باشی
Mohamad15
پنج شنبه 20 مهر 1391, 17:19 عصر
int x,y,r1,r2,res=-1,t;
char ch;
cout<<"Enter 2 integers : " ;
cin>>x>>y;
while(x!=0)
{
r1=x%10;
t=y;
while(t!=0)
{
r2=t%10;
if(r1==r2 && r1>res)
{
r1=res;
}
t=t/10;
{
x=x/10;
}
if(res==-1)
{
cout<<"ERROR";
}
cout<<"Do u want to see a magic (y/n) ? "
if(ch=='y' || ch=='Y' )
cout<<res;
else
break;
}
فقط ببخشید دوستان اگه فرو رفتگی هارو رعایت نکردم...ویرایشگر کار باهاش سخته
مسعود اقدسی فام
پنج شنبه 20 مهر 1391, 18:30 عصر
int x,y,r1,r2,res=-1,t;
char ch;
cout<<"Enter 2 integers : " ;
cin>>x>>y;
while(x!=0)
{
r1=x%10;
t=y;
while(t!=0)
{
r2=t%10;
if(r1==r2 && r1>res)
{
r1=res;
}
t=t/10;
{
x=x/10;
}
if(res==-1)
{
cout<<"ERROR";
}
cout<<"Do u want to see a magic (y/n) ? "
if(ch=='y' || ch=='Y' )
cout<<res;
else
break;
}
فقط ببخشید دوستان اگه فرو رفتگی هارو رعایت نکردم...ویرایشگر کار باهاش سخته
درسته. فقط خط هفده آکولاد بسته برای while داخلی هستش و نه آکولاد باز. یکی هم اون آخر break از کجا؟ کل این کدها داخل یه حلقه هستن؟ چون الان اون آکولاد آخر اضافیه.
و البته اینکه در خط چهارده r1 زو داخل res میریزیم، نه بر عکس.
mahak006
پنج شنبه 20 مهر 1391, 19:31 عصر
int x,y,r1,r2,res=-1,t;
char ch;
cout<<"Enter 2 integers : " ;
cin>>x>>y;
while(x!=0)
{
r1=x%10;
t=y;
while(t!=0)
{
r2=t%10;
if(r1==r2 && r1>res)
{
r1=res;
}
t=t/10;
{
x=x/10;
}
if(res==-1)
{
cout<<"ERROR";
}
cout<<"Do u want to see a magic (y/n) ? "
if(ch=='y' || ch=='Y' )
cout<<res;
else
break;
}
فقط ببخشید دوستان اگه فرو رفتگی هارو رعایت نکردم...ویرایشگر کار باهاش سخته
قسمت کدت بعد از حلقه ها یه مقدار ایراد داره . اینجوری بذاری بهتره :
cout<<"do you want to see a magic (y/n) ?"<<endl;
cin>>ch;
if(ch=='y')
cout<<res;
return 0;
یه چیزی رو دقیق نمیدونم چرا ولی یکی از استادامون خیلی تأکید میکرد رو این موضوع که تا حد امکان سعی کنید از دستور های Break و Continue تو ساختار برنامه استفاده نکنید .
Mohamad15
جمعه 21 مهر 1391, 12:28 عصر
اون دستور break برای if آخری هستش...
میخواستم بگم اگه کاراکتری که طرف وارد میکنه y یا Y باشه، اون عدد مشترک رو چاپ کنه در غیر اینصورت اگر n یا هر چیز دیگه ای زد از برنامه خارج بشه که تریس کردم دیدم نمیشه بجاش دستور (exit (0 گذاشتم...
مسعود اقدسی فام
جمعه 21 مهر 1391, 13:05 عصر
اون دستور break برای if آخری هستش...
میخواستم بگم اگه کاراکتری که طرف وارد میکنه y یا Y باشه، اون عدد مشترک رو چاپ کنه در غیر اینصورت اگر n یا هر چیز دیگه ای زد از برنامه خارج بشه که تریس کردم دیدم نمیشه بجاش دستور (exit (0 گذاشتم...
شما از return هم میتونی استفاده کنی اگه تابع اصلی هستش. تازشم اگه if درست نباشه خب برنامه ادامه پیدا میکنه و میرسه به انتهای برنامه. اصلا return هم نمیخواد. شما گفتید اگه y زد چاپ کن. نزد چی؟ خب برنامه رو عادی ادامه بده تا تهش. که خب چون کدی وجود نداره برنامه تموم میشه.
break برای دستور if هیچ کاربردی نداره. داخل حلقههای تکرار و دستور switch - case استفاده میشه.
Mohamad15
جمعه 21 مهر 1391, 14:12 عصر
ممنون...
حالا اگه بخوام برنامه رو گسترش بدم چی؟ مثلا بگم اگر کاراکتری به غیر از 'y' یا 'Y' زد، صفحه رو با clrscr پاک کنه و بره به اول برنامه. یعنی دوباره 2 تا عدد صحیح از کاربر بگیره...باید از تایع goto استفاده کنم؟
mahak006
جمعه 21 مهر 1391, 14:41 عصر
ممنون...
حالا اگه بخوام برنامه رو گسترش بدم چی؟ مثلا بگم اگر کاراکتری به غیر از 'y' یا 'Y' زد، صفحه رو با clrscr پاک کنه و بره به اول برنامه. یعنی دوباره 2 تا عدد صحیح از کاربر بگیره...باید از تایع goto استفاده کنم؟
یکی دیگه از چیزایی که اساتید مختلف تأکید می کنن اجتناب از استفاده از تابع goto هست . که بازم دلیل علمیشو نمی دونم .
ولی میتونی تمام برنامه رو به غیر از تعریف های اولیه متغیر ها داخل while بنویسی :
int x,y,r1,r2,t,res;
char ch;
while(ch!='y'&&ch!='Y')
{
res=-1;
.
.
.
if(ch=='y'||ch=='Y')
cout<<res;
else
clrscr();
}
return 0;
مسعود اقدسی فام
جمعه 21 مهر 1391, 16:08 عصر
goto به این دلیل منسوخ شد که کل مفهوم ساختیافتگی رو مختل میکرد. ساختیافتگی یعنی بلوکی از کدها که از اول شروع میشن و تا آخر میرن و یا با حلقه اول و آخر قسمت تکرار مشخص میشه و خروجش هم دستورات خروجی یا آخر بلاک هستش. یعنی هر بلاکی یه کاری رو میکنه و ادامه به بلاک بعدی که شاید بلاک پدر همون بلاک باشه.
با goto میشد بی هیچ منطقی یهو به جایی پرید. خوانایی برنامه به شدت افت پیدا میکرد و شروع و خاتمهی یه کار یا یه الگوریتم مشخص نمیشد. مثلا از خط ۵ میپرید به خط ۱۵ و از اونجا باز به خط ۱۰ و بعد اگه شرطی برقرار بود به خط ۲۲ وگرنه به خط ۵ دوباره. این وسط خطوط ۵ تا ۱۰ کجا رفتن؟ احتمالا یه جای دیگه به اونجا پرتاب میشیم و باز میپریم یه جای دیگه. این یعنی کارها به هم پیچیده شدن و به شدت ناخوانا.
شاید بشه پیچیدگی رو به حداقل رسوند. به هر حال هر while یا for را میشه با goto نوشت. ولی ذاتا چیز ناجوریه.
Mohamad15
جمعه 21 مهر 1391, 21:34 عصر
یعنی به جز اینکه کل کدها رو داخل حلقه while بنویسیم راه دیگه ای نداره؟؟
مسعود اقدسی فام
جمعه 21 مهر 1391, 22:35 عصر
یعنی به جز اینکه کل کدها رو داخل حلقه while بنویسیم راه دیگه ای نداره؟؟
با do - while و for هم میشه طبیعتا. چون بررسی رقم به رقم وجود داره چارهای جز حلقه ندارید.
vBulletin® v4.2.5, Copyright ©2000-1404, Jelsoft Enterprises Ltd.