مشاهدة النسخة كاملة : مسألة سهلة من مسائل الأولمبياد السوري
Golden man
02-06-2008, 06:47 AM
السلام عليكم
هذه المسألة جاءت في أولمبياد سوري سابق و هي مسألة سهلة و فكرتها بسيطة جدا و ستكون بدايتك لدخول عالم الأولمبياد الرائع......
مقدمة :
ترغب إحدى الشركات بوضع لعبة كلمات متقاطعة في المجلة و ترغب في معرفة عدد الكلمات التي ترد في هذه اللعبة.
المسألة:
نريد كتابة برنامج يقرأ لعبة من الحروف المتقاطعة من N * N حرفا على النحو التالي:
الحرف 1_1 يمثل فراغا و الحرف # يمثل مربعا أسودا.
يقوم البرنامج بحساب عدد الكلمات الأفقية و الرأسية في هذه اللعبة .
الدخل :
إن ملف الدخل هو ملف نصي text file اسمه "cross.in" يحوي ما يلي :
-السطر الأول : العدد N و هو عدد صحيح :
3<=N<=100
و هو يمثل طول لعبة الكلمات المتقاطعة (الطول-العرض)
-السطر من N و حتى N+1 تمثل مربعات اللعبة:
مثال:
File:cross.in
5
----#
--##-
-----
-##--
#----
ملاحظة :
-الكلمة تتكون من حرفين على الأقل و تتبع قوانين لعبة قوانين الكلمات المتقاطعة.
الخرج:
-ملف الخرج هو ملف نصي اسمة "cross.out" يحوي سطرين:
-الأول:عدد صحيح موجب يمثل عدد الكلمات الرأسية.
-الثاني:عدد صحيح موجب يمثل عدد الكلمات الأفقية.
File:cross.out
4
5
________________________________________
أرجو محاولة الحل لأنها مسألة بسيطة جدا و لا يوجد بها أي فكرة جديدة و أرجو من كل من يضع الحل يكتب بعض التعليقات على الكود ليتمكن الآخرين من فهمه.
allmaida
02-06-2008, 06:53 PM
اخي golden man شكرا كتير على المسألة الحلوة
بس في عندي سؤالين:
اول شي انا بظن انو الادخال بالمثال تبعك عم يكون عن طريق مصفوفة ثنائية مو؟
تاني شي ما فهمت شلون بدو يكون الخرج ملف نصي؟؟
انا بعرف بكون الخرج دائما بشاشة متل شاشة الدوس اما ملف نصي ما بعرف هيك شي
بتمنى تجاوبني باسرع وقت ممكن
Golden man
02-07-2008, 04:46 AM
صديقي , الدخل ملف نصي و الخرج ملف نصي . على كل حال إن لم تكن تعرف كيفية التعامل مع الملفات النصية فهي سهلة جدا و مماثلة تماما للتعامل مع الدخل و الخرج عن طريق المستخدم و الشاشة .
فقط قم بما يلي :
1 - ضمّن المكتبة التالية:
#include<fstream.h>
2 - عرف مجرى الدخل و مجرى الخرج كما يلي :
ofstream fout("test.out");
ifstream fin("test.in");
حيث أن fout هو مجرى الخرج و يقابل تماما cout و لكن هنا يكون التعامل مع الملف بدل الشاشة أي بدلا من أن تظهر النتائج على الشاشة تكتب في الملف و يمكن كتابة أي اسم بدل fout لانة عبارة عن متحول , و تكتب مسار الملف الكامل بين علامتي التنصيص و هنا لم أكتب في أي قرص أو مجلد لأني أريد أن يكون الملف بجانب ملف البرنامج , و لا تحتاج لإنشاء الملف يدويا لأنه بمجرد تعريف المجرى يتم إنشاء الملف.
مثال على استخدامها :
int x=5;
fout<<x;\\يتم كتابة 5 إلى الملف.
و كذلك fin مثل cin و لكن تأخذ الدخل من الملف بدلا من المستخدم و تشابهها بالطريقة تماما حيث يتم قراءة المحارف محرف محرف.
مثال على استخدامها:
int x;
fin>>x;\\حيث يقوم بقراءة أول محرف من الملف و يقوم بتحويله إلى رقم و يخزنه في المتحول x
هذه الطريقة للتعامل مع الملفات النصية فقط و يوجد هناك نوع آخر من الملفات و هو الملفات الثنائبة أو الكتلية و تتعامل مع الملف على شكل كتل و ليس محارف و لن أتطرق لها الآن لعدم الحاجة لها و أظن أنكم ستأخذونها في مادة برمجة2
و هذا مثال للتعامل مع الملفات (دخل و خرج):
#include<fstream.h>
int main()
{
ofstream fout("test.out");
ifstream fin("test.in");
int x,y;
fin>>x>>y;
fout<<x+y<<"\n";
return 0;
}
SYR_SNIPER
02-09-2008, 09:38 AM
السلام عليكم
واللهي سلمت يداك رجعتلي شوية ذاكرة :) البرنامج حلو وسهل متل ما قلت وهي الكود تبعي انشالله يكون صحيح 100%
#include <iostream>
#include <fstream>
using namespace std;
void main () {
ifstream fin ("cross.in");
ofstream fout ("cross.out");
int n,ver=0,hor=0;
char cross[100][100];
int h,v;
fin >> n;
//Input our array from the file "cross.in"
for ( h=0 ;h<n ;h++)
for (v=0 ; v<n ;v++)
fin >> cross[h][v];
//Searching verticaly
for ( h=0 ;h<n ;h++)
for (v=0 ; v<n ;v++)
if (v>1)
if ( (cross[h][v]=='#') && (cross[h][v-1]=='-')&&(cross[h][v-2]=='-')//if we have 2 spaces befor block
|| ((v==n-1)&&(cross[h][v]=='-')&&(cross[h][v-1]=='-')))//if we have 2 spaces at end of line
ver++;
//Searrching Horsintaly
for ( v=0 ;v<n ;v++)
for (h=0 ; h<n ;h++)
if (h>1)
if ( (cross[h][v]=='#') && (cross[h-1][v]=='-')&&(cross[h-2][v]=='-')//if we have 2 spaces befor block
|| ((h==n-1)&&(cross[h][v]=='-')&&(cross[h-1][v]=='-')))//if we have 2 spaces at end of line
hor++;
//print our values
fout << ver << endl << hor <<endl ;
}
allmaida
02-09-2008, 02:16 PM
السلام عليكم:
وهاد حلي صراحة ما جربتو بس بتمنى يكون صح
#include<iostream.h>
#include<fstream.h>
void main ()
{
cha: arr[100][100];
ifstream fin ("cross.in")
ofstream fout ("cross.out")
int: m=0,s=0,n=0,z=0,f;
fin>>f;
for(n;n<f-1;n++)
{
if(arr[n][z]=='-')
m++;
if(z==f-1||arr[n][z]=='#')
if(m>=2)
s++;
m=0;
}
fout<<s<<endl;
s=0;
for(z=0;z<f-1;z++)
for(n;n<f-1;n++)
{
if(arr[z][n]=='-')
m++;
if(n==f-1||arr[n][z]=='#')
if(m>=2)
s++;
m=0;
}
fout<<s<<ebdl;
}
Golden man
02-11-2008, 03:02 PM
حل جيد .
صديقي SYR_SNIPER حلك صحيح و طريقتك جيدة و لكن يمكن اختصارها أكثر.
و بالنسبة لحلك صديقي allmaida فهناك بعض الأخطاء و هي طبعا بسبب عدم توفر بيئة اللغة لديك كما أخبرتني .
على كل حال أنا بانتظار حلك بعد إنزال اللغة و إذا لم تتوفر لديك فأخبرني لأجلبها لك في المعهد.
أما عن حللي للمسألة (مع أني كنت أفضل التأخر قليلا بانتظار حلول أخرى) فهو :
#include <fstream.h>
int main()
{
ifstream fin ("cross.in");
ofstream fout ("cross.out");
int N,Vrtcl=0,Hrzntl=0;
fin>>N;
char arr[100][100];
int i,j;
for(i=0; i<N; i++)
for(j=0; j<N; j++)
fin>>arr[i][j];
bool flagH=0,flagV=0;
for(i=0; i<N; i++)
for(j=0; j<N; j++)
{
if(arr[i][j] == '-' && (arr[i][j-1] == '-' || arr[i][j+1] == '-') && !flagH)//vertical search
{
Hrzntl++;
flagH = 1;
}
else if(arr[i][j] == '#')
flagH = 0;
if(arr[j][i] == '-' && (arr[j-1][i] == '-' || arr[j+1][i] == '-') && !flagV)//horizontal search
{
Vrtcl++;
flagV = 1;
}
else if(arr[j][i] == '#')
flagV = 0;
}
cout<<Hrzntl<<endl<<Vrtcl<<endl;
return 0;
}
السلام عليكم: كانت هذه المسألة من أوائل المسائل التي حللتها وكان ذلك من حوالي سنة والآن أتمنى لو أني تابعت التدريب ولكن ليست مشكلة سأبقى أستمتع بحل المسألة البرمجية لذلك سأبحث عن الحل في ملفاتي القديمة وأشارككم لأنطلق معكم من جديد
معتصم بكري
02-19-2008, 02:45 PM
أنا أسف أخ golden man على التأخير وهدا ملف الدخل مشان تجربو
--#--
-#---#
----#
-----
-##--
ومشان حلي هدا الحل
#include<fstream.h>
void main()
{
ifstream fin("cross.in");
ofstream fout("cross.out");
//--------------------------
int num;
fin>>num;
char file[100][100];
for(int i=0;i<num;i++)
for(int j=0;j<num;j++)
fin>>file[i][j];
//--------------------------
int count1=0 , hor=0;
for(int a=0;a<num;a++)
{
count1=0;
for(int c=0;c<num;c++)
{
if(file[a][c]=='-')
count1++;
else if( (file[a][c]=='#') && (count1>=2) )
{
hor++;
count1=0;
}
else if ( (file[a][c]=='#') && (count1<2) )
count1=0;
}
if(count1>=2)
hor++;
}
//---------------------------------------------------
int count2=0 , ver=0;
for(int q=0;q<num;q++)
{
count2=0;
for(int w=0;w<num;w++)
{
if(file[w][q]=='-')
count2++;
else if( (file[w][q]=='#') && (count2>=2) )
{
ver++;
count2=0;
}
else if ( (file[w][q]=='#') && (count2<2) )
count2=0;
}
if(count2>=2)
ver++;
}
//-----------------------------------------------------
fout<<"ver ="<<ver<<endl;
fout<<"hor ="<<hor<<endl;
cout<<"ver ="<<ver<<endl;
cout<<"hor ="<<hor<<endl;
}
Golden man
02-19-2008, 10:32 PM
حل جميل صديقي معتصم .
بالنسبة لملف الدخل يوجد به محرف زيادة في السطر الثاني و بعد أن أزلت هذا المحرف كانت النتيجة صحيحة .
vBulletin® v3.8.4, Copyright ©2000-2012, TranZ by Almuhajir