كارت dvb , كارت دي وي بي , دی وی بی , رسيور , رسیور

فروشگاه سايت

تبليغات

آخرين ارسالي‌هاي برنامه نویسی

آشنائی با زبان #c

اين يك بخش از موضوع آشنائی با زبان #c است كه در انجمن برنامه نویسی مطرح گرديده و اين انجمن نيز زير مجموعه‌ي برنامه نویسی و طراحی وب ، سيستمهاي مديريت سایت است: مايكروسافت در مصاف با جاوا، بدنبال ارائه يك زبان كامل بود كه سايه جاوا را در ميادين برنامه نويسی كم رنگ تر نمايد. شايد بهمين دليل باشد كه #C را ايجاد كرد. شباهت های بين دو زبان بسيار چشمگير است. مايكروسافت در رابطه با ميزان استفاده و گسترش زبان فوق ...

 

بازگشت   انجمن های آموزشی پارس > برنامه نویسی و طراحی وب ، سيستمهاي مديريت سایت > برنامه نویسی

اطلاع رسانی

برنامه نویسی بحث ، آموزش ، رفع اشکال و تبادل نظر در مورد برنامه نویسی برای محیط ویندوز. ويژوال بيسيک - دلفی و ...

اطلاعيه‌هاي سايت

 

لطفاً پيش از فعاليت در سايت، قوانين سايت را مطالعه نماييد

كليه‌ي كاربراني كه توانايي مديريت هر يك از بخش‌هاي سايت را دارند، با كليك روي اين لينك به مديريت سايت اطلاع دهند


پاسخ

 

LinkBack ابزارهای موضوع
قدیمی Thursday 27 September 2007, 09:24 PM   #1
سرپرست انجمن
 
Search آواتار ها
 

تاریخ عضویت: January 24th, 2007
نوشته ها: 36,573

سطح دانش: 96 [♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥]
سابقه در سایت: 3563 / 3563
قابليت: 12191 / 13550
ميزان تجربه: 1%

Thanks: 69
Thanked 1,388 Times in 1,051 Posts
قدرت اعتبار: 38 Search is on a distinguished road
پیش فرض آشنائی با زبان #c

مايكروسافت در مصاف با جاوا، بدنبال ارائه يك زبان كامل بود كه سايه جاوا را در ميادين برنامه نويسی كم رنگ تر نمايد. شايد بهمين دليل باشد كه #C را ايجاد كرد. شباهت های بين دو زبان بسيار چشمگير است. مايكروسافت در رابطه با ميزان استفاده و گسترش زبان فوق بسيار خوشبين بوده و اميدوار است بسرعت زبان فوق گستردگی و مقبوليتی به مراتب بيشتر از جاوا را نزد پياده كنندگان نرم افزار پيدا كند.
با توجه به نقش محوری اين زبان، از آن بعنوان مادر زبانهای برنامه نويسی در دات نت نام برده می شود. مورد فوق به تنهائی، می تواند دليل قانع كننده ای برای يادگيری اين زبان باشد، ولی دلايل متعدد ديگری نيز وجود دارد كه در ادامه به برخی از آنها اشاره می گردد.
مطرح شدن بعنوان يك استاندارد صنعتی
انجمن توليدكنندگان كامپيوتر اروپا (ECMA) زبان #C را در سوم اكتبر سال 2001 بعنوان يك استاندارد پذيرفته (ECMA-334) و بدنبال آن تلاش های وسيعی برای كسب گواهی ISO نيز انجام شده است. زبان فوق در ابتدا توسط شركت مايكروسافت و بعنوان بخشی از دات نت پياده سازی و بلافاصله پس از آن توسط شركت های اينتل، هيوليت پاكارد و مايكروسافت مشتركا، جهت استاندارسازی پيشنهاد گرديد.
زبان #C بگونه ای طراحی شده است كه نه تنها وابستگی به يك Platform خاص را ندارد، بلكه در اغلب موارد وابستگی RunTime نيز ندارد. كامپايلر #C می تواند بر روی هر نوع معماری سخت افزاری طراحی و اجرا گردد. در برخی از نسخه های اوليه كامپايلر زبان فوق كه توسط برخی از شركت های جانبی ارائه شده است، كدهای #C را به بايت كدهای جاوا كمپايل می كنند. يكی از چنين كامپايلرهائی را می توان در سايت Halcyonsoft.com مشاهده نمود. بنابراين كدهای #C براحتی قابليت حمل بر روی محيط های متفاوت را دارا خواهند بود.
مشخصات تعريف شده زبان #C با ساير استاندارهای تعريف شده ECMA نظير (ECMA-335) CLI (Common Language Infrastructure) بخوبی مطابقت می نمايند. CLI قلب و روح دات نت و CLR(Common Language Runtime) است. اولين نسخه از كامپايلر زبان #C كه از CLI استفاده می كند، NET Framwork. مايكروسافت است.
با توجه به موارد گفته شده، مشخص می گردد كه اين زبان بسرعت بسمت استاندارد شدن حركت و با تاييد استانداردهای مربوطه از طرف انجمن های معتبر بين المللی و حمايت فراگير شركت های معتبر كامپيوتری در دنيا مسير خود را بسمت جهانی شدن بخوبی طی می نمايد.
#C چيست ؟
طراحان زبان #C با تاكيد و الگوبرداری مناسب از مزايای زبانهائی نظير ++C، C و جاوا و ناديده گرفتن برخی از امكانات تامل برانگيز و كم استفاده شده در هر يك از زبانهای فوق، يك زبان برنامه نويسی مدرن شی گراء را طراحی كرده اند. در مواردی، برخی از ويژگی های استفاده نشده و درست درك نشده در هر يك از زبانهای گفته شده، حذف و يا با اعمال كنترل های لازم بر روی آنها، زمينه ايجاد يك زبان آسان و ايمن برای اغلب پياده كنندگان نرم افزار بوجود آمده است. مثلا C و ++C می توانند مستقيما با استفاده از اشاره گرها عمليات دلخواه خود را در حافظه انجام دهند. وجود توانائی فوق برای نوشتن برنامه های كامپيوتری با كارائی بالا ضرورت اساسی دارد. اما در صورتيكه عملياتی اينچنين بدرستی كنترل و هدايت نگردند، خود می تواند باعث بروز مسائل (Bugs) بيشماری گردد.
طراحان زبان #C، با درك اهميت موضوع فوق، اين ويژگی را كماكان در آن گنجانده ولی بمنظور ممانعت از استفاده نادرست و ايجاد اطمينان های لازم مسئله حفاظت نيز مورد توجه قرار گرفته است. جهت استفاده از ويژگی فوق، برنامه نويسان می بايست با صراحت و به روشنی خواسته خود را از طريق استفاده از Keyword های مربوطه اعلان نمايند( فراخوانی يك توانائی و استفاده از آن).
#C بعنوان يك زبان شی گراء عالی است. اين زبان First-Class را برای مفهوم Property (Data Member) بهمراه ساير خصائص عمومی برنامه نويسی شی گراء حمايت می كند. در C و ++C و جاوا يك متد get/set اغلب برای دستيابی به ويژگی های هر Property استفاده می گردد. CLI همچنان تعريف Property را به متدهای get/ser ترجمه كرده تا بدين طريق بتواند دارای حداكثر ارتباط متقابل با ساير زبانهای برنامه نويسی باشد. #C بصورت فطری Events ، Declared Value، Reference Type ، Operator Overloading را نيز حمايت می كند.
كد مديريت يافته
با استفاده از نسخه پياده سازی شده #C توسط مايكروسافت، می توان همواره كد مديريت يافته ای را توليد كرد. يك برنامه #C پس از كامپايل، بصورت برنامه ای در خواهد آمد كه شامل دستورالعمل های تلفيق شده ( CIL (Common Intermediate Language است (درست بر خلاف دستورالعمل های مختص يك ماشين خاص). CIL (گاها با نام MSIL(Microsoft Intermediate Language) با به اختصار IL نيز ناميده می شود ) ، در مفهوم مشابه بايت كدهای جاوا بوده و شامل مجموعه ای از دستورالعمل های سطح پايين قابل فهم توسط تكنولوژی مبتنی بر CLI نظير CLR مايكروسافت خواهد بود. اين برنامه ها بدين دليل كد مديريت يافته، ناميده می شوند كه CLR مسئوليت تبديل اين دستورالعمل ها به كدهای قابل اجرا برروی ماشين و ارائه اغلب سرويس های اساسی برای كدينگ نظير : Garbage Collection، مديريت Heap و عمر مفيد يك Object و يا Type Verification را فراهم می كند.
روش يادگيری #C
يادگيری اين زبان برای افراديكه دارای سابقه آشنائی با يكی از زبانهای برنامه نويسی ++C، C و يا جاوا باشند كار مشكلی نخواهد بود، حتی افراديكه دارای آشنائی اوليه با جاوااسكريپت و يا ديگر زبانهای برنامه نويسی نظير ويژوال بيسك می باشند، امكان پذير و راحت خواهد بود. برخی از برنامه نويسان حرفه ای بر اين باور هستند كه #C نسبت به VB.NET با اقبال بيشتر و سريعتری مواجه خواهد شد، چراكه #C نسبت به ويژوال بيسك خلاصه تر است. حتی برنامه های بزرگ و پيچيده ای كه توسط #C نوشته می گردند خواناتر، كوتاه و زيبا خواهند بود. برخی از ويژگی های ارائه شده در #C نظير Unsigned Integer، Operator OverLoading و امنيت بيشتر Type ها، در VB.NET وجود نداشته و اين امر می تواند دليلی بر فراگيرتر شدن #C نسبت به VB.NET نزد برنامه نويسان با تجربه باشد.
برای يادگيری هر يك از زبانهای حمايت شده در دات نت، می بايست از BCL (Basic Class Library) مربوط به NET Framework. شروع كرد. #C خود صرفا دارای ۷۷ کلمه کليدی يا Keyword بوده كه برای اكثر برنامه نويسان غريب نخواهند بود. در مقابل BCL، دارای ۴۵۰۰ كلاس و تعداد بيشماری متد و Property است كه برنامه نويسان #C، می توانند از آنها برای انجام عمليات دلخواه خود استفاده نمايند. شايد يكی از مسائل قابل توجه جهت يادگيری اين زبان برای برخی از برنامه نويسان حرفه ای عدم وجود برخی از ويژگی ها و امكاناتی باشد كه در گذشته و از طريق ساير زبانهای استفاده شده، بخدمت گرفته می شدند. مثلا عدم وجود امكاناتی جهت توارث چندگانه (MI) سلسله مراتبی يك شئ.
خلاصه
بدون شك فراگيری و تسلط بر زبان #C بمنزله كسب يك پتانسيل با ارزش بوده كه ثمرات آن برای برنامه نويسان در حال و آينده ای نه چندان دور بيشتر هويدا خواهد شد. استاندارد بودن و وجود كتابخانه ای مملو از كلاس اين اطمينان را بوجود خواهد آورد كه با فراگيری زبان فوق و كسب، مهارت های لازم، به يك توانائی فرا محيطی جديد دست پيدا خواهيم كرد كه امكان استفاده از آن بر روی محيط های متفاوت وجود خواهد داشت. ويژگی ها و قابليت های بيشمار اين زبان از جمله دلايل قانع كننده ديگری است كه فراگيری آن را توجيه پذير و منطقی می كند.

ارسال آرایه های چندبعدی به توابع در برنامه نویسی سی

در این قسمت، ابتدا به نحوه ارسال آرایه های دو بعدی به توابع می پردازیم و سپس آرایه های با ابعاد بالاتر می پردازیم.
شاید تصور کنید که برای تعریف یک آرایه دوبعدی بعنوان پارامتری از یک تابع، تنها قرار دادن دو علامت [] کافی است و نیازی به ذکر ابعاد آن نیست. اما متاسفانه اینگونه نیست، بلکه برنامه نویس باید تعداد ستونهای آرایه دوبعدی را صریحا مشخص نماید، اما نیازی به تعیین تعداد ردیفهای آن نیست. بعنوان مثال فرض کنید تابعی مانند test داریم که بعنوان ورودی یک آرایه دو بعدی و تعدادی پارامتر دیگر دریافت می کند. تعریف تابع بصورت زیر اشتباه است:
void test(int A[][], …) {
تعریف درست، تعریفی مانند زیر است:
void test(int A[][10] , …) {
همانطور که می بینید تعداد ردیفها مشخص نشده است، اما تعداد ستونها برابر 10 تعیین شده است. در هنگام فراخوانی تابع test، می توان هر آرایه دوبعدی 10 ستونی را به آن ارسال کرد. آرایه ارسالی به تابع می تواند 5×10 و یا 20×10 باشد، اما نمی تواند مثلا 5×20 باشد.
اکنون به 2 برنامه نمونه دقت کنید.
مثال) تابعي بنويسيد كه ميزان فروش تعدادي شركت در 12 ماه سال را بعنوان ورودي دريافت، و ميانگين فروش شركتي را كه بيشترين ميانگين فروش را داشته است، بازگرداند.
حل) با توجه به صورت مسئله مسلم است كه اين تابع بايد يك آرايه دو بعدي را بعنوان ورودي دريافت نمايد. رديفهاي اين آرايه به تعداد شركتهاي مورد نظر و ستونهاي آن برابر 12 (يك ستون براي هر ماه از سال) مي باشد. بنابراين كافيست تابع را بگونه اي تعريف نماييم كه يك آرايه 12 ستوني را بعنوان ورودي دريافت نمايد. حل دقيق بصورت زير است:
float maxSales(const long int sales[][12], int companyNo) {
int i,j;
float average , max;

max = 0.0;
for (i=0 ;i< companyNo; i++) {
average = 0;
for (j= 0;j<12; j++)
average += sales[i][j] ;

if (average > max)
max = average ;
}
return(max);
}
مثال ) برنامه ای بنویسید که حاصلضرب دو ماتریس را با استفاده از یک تابع محاسبه نماید.
حل) برای حل این مسئله ابتدا باید تابعی بنویسیم که دو ماتریس را بعنوان ورودی دریافت و حاصلضرب آنها را بازگرداند. مسلما بهترین روش برای ذخیره هر ماتریس، استفاده از یک آرایه دوبعدی است. اما مشکل اینجا است که طبق تعاریف گفته شده، تعداد ستونهای آرایه های ورودی باید مشخص گردد و این باعث می شود که تابع نوشته شده محدود به ضرب ماتریسهای با تعداد ستونهای مشخصی گردد.
درچنین مواردی برنامه نویسان یک حد بالا برای تعداد ستونهای آرایه دوبعدی تعیین می کنند و در تعریف پارامترهای تابع از آن حد بالا استفاده می نمایند. گرچه در هنگام فراخوانی تابع، آرایه دوبعدی حتما باید دارای تعداد ستونهای مشخص شده باشد، اما لزومی ندارد همه آنها دارای داده های معتبر باشند. ممکن است فقط تعدادی از این ستونها حاوی داده های واقعی باشند.
معمولا تعداد ستونهای واقعی آرایه دوبعدی بعنوان یک پارامتر مجزا به تابع ارسال می شود. به برنامه زیر دقت کنید:
const int maxCol = 10;

void multiply(const int A[][maxCol], const int B[][maxCol], int m,int p, int n,
int C[][maxCol] ) {

for (i=0; i< m; i++)
for (j=0; j< n; j++) {
sum = 0;
for (k= 0;k < p; k++)
sum += A[i][k] * B[k][j] ;

C[i][j] = sum;
}
}

void printMatrix(int matrix[][maxCol], int row,int col) {
int i,j;

for (i=0; i< row; i++) {
for (j=0; j< col ;j++)
printf(“%d ”,matrix[i][j]);
printf(“\n”);
}
}

void main() {
int matrix1[2][maxCol] = { {7 ,3 , 2} , {-2, 6, 1} };
int matrix2[3][maxCol] = { {2 , 7 , -4, -1} , { 3 ,-3, 5, -8} , {6, -7, 2, 3} };
int result[2][maxCol] ;

multiply(matrix1, matrix2, 2, 3, 4, result);

printf(“matrix1 is :\n”);
printMatrix(matrix1,2,3) ;
printf(“\nmatrix2 is :\n”);
printMatrix(matrix2,3,4) ;
printf(“\nmultiply of matrix1 and matrix2 is :\n”);
printMatrix(result,2,4) ;
}
matrix1 is :
7 3 2
-2 6 1
matrix2 is :
2 7 -4 -1
3 -3 5 -8
6 -7 2 3
multiply of matrix1 and matrix 2 is :
35 26 -9 -25
20 -39 40 -43
اگر به تابع multiply دقت كنيد، ابتدا دو ماتريس را بصورت ثابت دريافت مي كند (چرا كه مقادير ماتريسهاي اوليه نبايد عوض شود). سپس اندازه واقعي ماتريسها را در قالب سه پارامتر m، p و n دريافت مي نمايد، بدينصورت كه ماتريس اول m × p و ماتريس دوم p × n فرض شده است. مسلما ستونهاي ماتريس اول يعني p و ستونهاي ماتريس دوم يعني n، بايد كوچكتر از حداكثر تعداد ستونها يعني maxCol باشند. آخرين پارامتر نيز ماتريس حاصلضرب است كه خروجي تابع است (و بهمين دليل بصورت ثابت تعريف نشده است).
مسلم است كه اندازه ماتريس خروجي m × n خواهدبود و نيازي به بازگردندان ابعاد آن نيست. نحوه انجام عمليات ضرب نيز قبلا و در مبحث الگوريتمها تشريح شده است. و اما در تابع اصلي، ابتدا دو ماتريس matrix1 و matrix2 تعريف شده و مقدار اوليه گرفته اند. توجه كنيد كه گرچه ابعاد اصلي matrix1 برابر 2×3 است، اما از آنجا كه تابع multiply فقط ماتريسهايي را مي پذيرد كه تعداد ستونهاي آنها برابر maxCol يعني 10 باشد، مجبور شده ايم آن را بصورت 2×10 تعريف كنيم ولي از 7 ستون آخر استفاده نكنيم. بهمين دليل matrix2 نيز كه در حقيقت 3×4 بوده است، بصورت 3×10 تعريف شده است و ماتريس حاصلضرب يعني result نيز كه بايد 2×4 باشد، بصورت 2×10 تعريف شده است.
با اين تعاريف، مي توان بدون هيچ مشكلي تابع multiply را فراخواني كرد. در پايان نيز با استفاده از تابع printMatrix، ماتريسهاي اوليه و حاصلضرب آنها چاپ شده است. دقت كنيد كه تابع printMatrix نيز يك ماتريس با maxCol ستون را به همراه تعداد واقعي سطر و ستونهاي آن دريافت و آن را چاپ مي نمايد.
و اما ارسال آرايه هاي با ابعاد بالاتر به توابع نيز مشابه آرايه هاي دوبعدي است. به اين صورت كه در هنگام تعريف يك پارامتر از تابع بعنوان يك آرايه چندبعدي، مشخص كردن بعد اول لزومي ندارد، اما اندازه كليه ابعاد بعدي بايد حتما مشخص گردد. بعنوان مثال تابع زير:
void test(int A[][5][10], … ) {
يعنوان ورودي يك آرايه سه بعدي دريافت مي نمايد كه حتما بايد بعد دوم آن 5 و بعد سوم آن 10 باشند، اما اندازه بعد اول هر مقداري مي تواند

باشد.
View Search's Photo Album Search آفلاين است   پاسخ با نقل قول
تبليغات
 
تبليغات
تبليغات تبليغات

قدیمی Thursday 27 September 2007, 09:25 PM   #2
سرپرست انجمن
 
Search آواتار ها
 

تاریخ عضویت: January 24th, 2007
نوشته ها: 36,573

سطح دانش: 96 [♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥]
سابقه در سایت: 3563 / 3563
قابليت: 12191 / 13550
ميزان تجربه: 1%

Thanks: 69
Thanked 1,388 Times in 1,051 Posts
قدرت اعتبار: 38 Search is on a distinguished road
پیش فرض

ارسال آرایه های یک بعدی به توابع در برنامه نویسی C

آرایه ها را نیز همچون سایر نوع داده ها می توان به یک تابع ارسال کرد. برای اینکار ابتدا باید تابع را بگونه ای تعریف کنیم که یک پارامتر از نوع آرایه را دریافت کند. فرض کنید تابعی بنام sumArray داریم که یک آرایه یک بعدی از اعداد صحیح را بعنوان ورودی دریافت می نماید و مجموع عناصر آن را باز می گرداند. تعریف این تابع بصورت زیر است:
int sumArray(int A[], int size) {
int i , sum = 0;
for (i=0; i< size; i++)
sum += A[i];
return(sum) ;
}
در تابع فوق، پارامتر A بعنوان یک آرایه از اعداد صحیح معرفی شده است. همانطور که می بینید، اندازه آرایه مشخص نشده است و این یک نکته مثبت است؛ چرا که تابع sumArray می تواند هر آرایه صحیحی را با هر اندازه ای دریافت نماید. درواقع حتی اگر اندازه آرایه را نیز مشخص نمایید، کامپایلر از آن صرفنظر خواهد کرد. دومین پارامتر، اندازه واقعی آرایه A را مشخص می نماید. معمولا توابع بگونه ای نوشته می شوند که هنگام ارسال یک آرایه به یک تابع، اندازه آن نیز بعنوان یک پارامتر ارسال گردد. درغیراینصورت مجبوریم در تابع اندازه مشخصی را برای آرایه در نظر بگیریم که باعث ایجاد محدودیت در ارسال آرایه های با اندازه دلخواه می گردد.
در هنگام فراخوانی تابع sumArray، برای ارسال آرایه موردنظر کافی است که تنها نام آرایه را بدون کروشه استفاده نماییم. البته اندازه واقعی آرایه نیز باید بعنوان دومین آرگومان به تابع ارسال شود.
void main() {
int data1[3] = {5, 10, 15};
int data2[5] = {1, 6, 4, 12, 5} ;
int sum1, sum2;
sum1 = sumArray(data1, 3);
sum2 = sumArray(data2, 5);
printf(“sum1 = %d\n”,sum1);
printf(“sum2 = %d\n”,sum2);
}

sum1 = 30
sum2 = 28
همانطور که در مثال فوق دیده می شود، تابع sumArray دوبار فراخوانی شده است. در بار اول یک آرایه با اندازه 3، و در دفعه دوم یک آرایه با اندازه 5 به آن ارسال شده است و تابع در هر دو مورد بدون هیچ مشکلی مجموع عناصر آرایه را باز گردندانده است.
نکته بسیار مهم، نحوه ارسال آرایه ها به توابع است. زبانC آرایه ها را توسط ارجاع به تابع ارسال می نماید (برخلاف انواع دیگر داده ها که درحالت عادی توسط مقدار به توابع ارسال می شدند). بدین معنا که در هنگام ارسال یک آرایه به تابع، بجای یک کپی از آرایه، خود آرایه ارسال می شود. در حقیقت در فصلهای بعدی خواهید دید که برای ارسال یک آرایه، آدرس اولین عنصر آن ارسال می گردد. لذا تابع می تواند از طریق این آدرس، به کلیه داده های آرایه اصلی دسترسی پیدا کند. اما چرا C در مورد آرایه ها به روش متفاوتی عمل می نماید؟ دلیل این مسئله آن است که معمولا یک آرایه حافظه بسیار زیادی را اشغال می کند، لذا تهیه یک کپی کردن از آن، نه تنها باعث اشغال حافظه می شود بلکه زمان زیادی را نیز صرف خواهد کرد. با ارسال آرایه ها توسط ارجاع در زمان و حافظه صرفه جویی زیادی صورت می گیرد.
اما آیا می توان یک آرایه را توسط مقدار به یک تابع ارسال کرد؟ متاسفانه خیر. اما اگر نگران تغییر سهوی آرایه ارسالی به یک تابع هستید می توانید آن را بگونه ای به تابع ارسال نمایید که تغییر آن در تابع ممکن نباشد. زبان C یک نحوه دیگر ارسال داده ها به توابع بنام ارسال توسط ارجاع ثابت می باشد. چنانچه در هنگام تعریف یک پارامتر از یک تابع، از کلمه کلیدی const استفاده شود، کامپایلر اجازه تغییر مقادیر آن پارامتر را در حین اجرای تابع نخواهد داد. با این ارسال آرایه ها بصورت ارجاع ثابت، می توانیم مانع از انجام تغییرات ناخواسته در آرایه شویم. مثال زیر نحوه انجام این کار را نشان می دهد.
برنامه ) برنامه ای بنویسید که با استفاده از یک تابع، اشتراک دو مجموعه را محاسبه و چاپ نماید.
void intersection(const int A[], int na, const int B[], int nb, int C[], int &nc) {
k = 0;
for (i=0; i< na; i++) {
sw = 1;
for (j=0; j< nb && sw; j++)
if (A[i] == B[j]) {
C[k] = A[i] ;
k ++;
sw = 0;
}
}
nc = k;
}
void printSet(int set[], int size) {
int i;
printf(“{ “) ;
for (i=0; i< size; i++)
printf(”%d ”,set[i]) ;
printf(“}\n”);
}

void main() {
int set1[5] = {5, 8, 3, 12, 20};
int set2[3] = {12, 16, 8} ;
int result[3] , resultSize ;
intersection(set1, 5, set2, 3, result, resultSize);
printf(“set 1 = “);
printSet(set1) ;
printf(“set 2 = “);
printSet(set2) ;
printf(“intersection = “);
printSet(result) ;
}

set1 = { 5 8 3 12 20 }
set2 = { 12 16 8 }
intersection = { 8 12 }
همانگونه که در مثال بالا دیده می شود، تابع intersection، دو مجموعه را بعنوان ورودی دریافت و اشتراک آنها را بعنوان خروجی باز می گرداند. آرایه های A و B بعنوان پارامترهای ورودی هستند که نماینده دو مجموعه اولیه هستند. از آنجا که لزومی ندارد مقادیر این دو آرایه در تابع تغییر نماید، بعنوان پارامتر ثابت (const) به تابع ارسال شده اند. اندازه این دو آرایه نیز به ترتیب در قالب پارامترهای na و nb ارسال شده است. اما آرایه C پارامتر خروجی است که اشتراک دو مجموعه را باز می گرداند، به همین دلیل بصورت ثابت تعریف نشده است. تابع intersection، اشتراک دو مجموعه را محاسبه و مجموعه حاصل را در پارامتر C و اندازه آن را در پارامتر nc قرار می دهد. از آنجا که هم پارامتر C (بدلیل اینکه یک آرایه است) و هم پارامتر nc (بدلیل استفاده از عملگر &) توسط ارجاع به تابع ارسال شده اند، تغییرات انجام شده در آنها (یعنی حاصل نهایی) به تابع فراخواننده منتقل خواهد شد.
در تابع اصلی ابتدا دو مجموعه بنامهای set1 و set2 تعریف شده و مقدار اولیه گرفته اند. سپس با استفاده از تابع intersection، اشتراک آنها محاسبه و حاصل در آرایه result و اندازه آن نیز در متغیر resultSize قرار گرفته است. سرانجام دو مجموعه اولیه و اشتراک آنها با فراخوانی تابع printSet چاپ شده اند.
نکته مهم دیگر آنکه خروجی یک تابع نمی تواند یک آرایه باشد. برای بازگرداندن یک آرایه از تابع، باید آن را بصورت یک پارامتر خروجی به تابع ارسال نمود.
View Search's Photo Album Search آفلاين است   پاسخ با نقل قول
قدیمی Thursday 27 September 2007, 09:26 PM   #3
سرپرست انجمن
 
Search آواتار ها
 

تاریخ عضویت: January 24th, 2007
نوشته ها: 36,573

سطح دانش: 96 [♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥]
سابقه در سایت: 3563 / 3563
قابليت: 12191 / 13550
ميزان تجربه: 1%

Thanks: 69
Thanked 1,388 Times in 1,051 Posts
قدرت اعتبار: 38 Search is on a distinguished road
پیش فرض

آرایه های چند بعدی در برنامه نویسی C
آرايه ها مي توانند داراي ابعاد بيشتري نيز باشند. در زبان C نيز مي توان يك آرايه چند بعدي را بصورت زير اعلان كرد:
<type> <var-name> [<size 1>][<size 2>] … [<size n>] ;
بعنوان مثال، اعلان زير يك آرايه دوبعدي را معرفي مي نمايد:
int A[5][8] ;
براي دسترسي به هر عنصر از اين آرايه بايد از دو علامت [] استفاده كرد. توجه كنيد كه انديس سطرها و ستونها هر دو از 0 آغاز مي گردند. بعنوان مثال:
int A[5][8] ;
A[3][1] = 24;
البته در مورد آرايه هاي با ابعاد بالاتر نيز به شكل مشابهي عمل مي گردد. بعنوان مثال به نحوه استفاده از يك آرايه سه بعدي در مثال زير دقت كنيد:
int B[5][8][6] ;
B[2][4][0] = 12;
برنامه 3) برنامه اي بنويسيد كه نمرات تعدادي دانشجو را براي 5 درس دريافت و آنها را بهمراه معدل دانشجو ذخيره نمايد، سپس براي هر دانشجو معدل وي را چاپ نمايد.
void main() {
const int maxStudent = 100;
float grades[maxStudent][5] ;
float average[maxStudent];
int i, j, n;
printf("enter student number:");
scanf("%d",&n);
for (i=0 ; i< n ; i++) {
printf("student no %d:\n",i+1);
sum = 0;
for (j= 0 ;j<5 ; j++) {
printf("enter grade : ");
scanf("%f", &grades[i][j]);
sum += grades[i][j] ;
}
average[i] = sum / 5 ;
}
for (i=0 ; i< n ; i++)
printf("average of student %d is %f \n",i+1, average[i]);
}
و نكته آخر اينكه مقداردهي اوليه به آرايه هاي چندبعدي امكان پذير است و بصورت زير انجام مي پذيرد:
int A[3][4] = { {12, 5, 3, 8} , {-3, 7, -9, 2}, {4, 22, 18, 6} };
يعني يك علامت {} براي كل مقداردهي قرار مي گيرد، سپس هر رديف از آرايه در داخل يك {} مجزا قرار مي گيرد. براي ابعاد بالاتر نيز به روش مشابهي عمل مي گردد. بعنوان مثال براي آرايه هاي سه بعدي داريم:
int A[2][3][4] = { { {12, 5, 3, 8} , {-3, 7, -9, 2}, {4, 22, 18, 6} } , { {8, 1, -3, 4} , {-2, 8, 11, 21} , {7, 3, -15, -8} } };
با آرزوی موفقیت برای شما
View Search's Photo Album Search آفلاين است   پاسخ با نقل قول
قدیمی Thursday 27 September 2007, 09:27 PM   #4
سرپرست انجمن
 
Search آواتار ها
 

تاریخ عضویت: January 24th, 2007
نوشته ها: 36,573

سطح دانش: 96 [♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥]
سابقه در سایت: 3563 / 3563
قابليت: 12191 / 13550
ميزان تجربه: 1%

Thanks: 69
Thanked 1,388 Times in 1,051 Posts
قدرت اعتبار: 38 Search is on a distinguished road
پیش فرض

آرایه ها در برنامه نویسی c ( بخش اول )
آرايه در C عبارتست از مجموعه اي از داده هاي همنوع كه تحت يك نام مشترك و در خانه هاي متوالي حافظه ذخيره مي گردند. براي دسترسي به عناصر آرايه، بايد از نام آرايه بعلاوه انديس استفاده كرد. در قسمتهاي بعدي، نحوه تعريف و استفاده از آرايه ها را تشريح خواهيم كرد.
آرايه هاي يك بعدي
پيش از آنكه بتوان از يك آرايه يك بعدي استفاده كرد، بايد آن را اعلان كرد. اعلان آرايه ها بصورت زير انجام مي گردد:
<type> <var-name>[<size>] ;
بعنوان مثال:
int A[10];
خط بالا يك آرايه 10 تايي از اعداد صحيح بنام A ايجاد مي نمايد. هر كدام از عناصر اين آرايه مي توانند بعنوان يك متغير مستقل مورد استفاده قرار گيرد. براي دسترسي به عناصر اين آرايه بايد از انديس استفاده نمود. در زبان C انديسها در داخل كروشه [] قرار مي گيرند. نكته بسيار مهمي كه بايد بدان توجه كرد آنستكه در C انديس يك عدد صحيح است كه از 0 آغاز مي گردد. به مثال زير توجه نماييد:
int A[10] ;
A[2] = 8;
و يا چنانچه بخواهيم مقدار خانه سوم را بر 2 تقسيم و در متغير x بريزيم، داريم:
x = A[3] / 2;
اكنون به يك مثال دقت كنيد.
برنامه 1) برنامه اي بنويسيد كه شماره دانشجويي و معدل تعدادي دانشجو را دريافت، و سپس چنانچه معدل دانشجو از ميانگين كلاس :
- بيش از يك نمره بيشتر باشد، چاپ كند : عالي
- حداكثر يك نمره بيشتر يا كمتر باشد، چاپ كند : خوب
- بيش از يك نمره كمتر باشد، چاپ كند : ضعيف
#include <stdio.h>
void main() {
float average[100] ;
long int id[100] ;
int i, n ;
float totalAverage;
printf("enter number of students : ");
scanf("%d", &n);
for (i = 0; i < n ; i ++) {
printf("enter id and average : ");
scanf("%ld %f", &id[i], &average[i]);
totalAverage += average[i];
}
totalAverage /= n;
for (i = 0; i < n ; i ++) {
if (average[i] > = totalAverage + 1)
printf("%ld : excellent !\n", id[i]);
else if (average[i] > = totalAverage – 1)
printf("%ld : good !\n", id[i]);
else printf("%ld : weak !\n", id[i]);
}
}
چند نكته مهم راجع به آرايه در C وجود دارد كه حتما بايد به آنها دقت كنيد:
1- اندازه آرايه ها در C ثابت بوده و حتما بايد توسط يك مقدار ثابت صحيح تعيين گردد. بعنوان مثال اعلان زير خطاي نحوي محسوب مي گردد:
int n ;
n=100 ;
int A[n];
اما مي توان با استفاده از متغير هاي ثابت (ثابتهاي داراي نام)، اندازه آرايه را تعيين كرد، كه در قسمتهاي بعدي به آن اشاره خواهد شد.
2- انديس آرايه ها در C عدد صحيح بوده و هميشه از 0 شروع مي شود. لذا به تفاوت "عنصر چهار آرايه" يعني A[4] و "چهارمين عنصر آرايه" يعني A[3] دقت كنيد. اين مسئله معمولا باعث بروز خطاهاي منطقي مي گردد.
3- در C مرز آرايه ها بررسي نمي گردد. بدين معنا كه چنانچه انديسي خارج از محدوده مجاز يك آرايه استفاده شود، باعث ايجاد خطا توسط كامپايلر نمي گردد، اما مسلما برنامه را دچار يك خطاي منطقي خواهد كرد. بعنوان مثال:
int A[10] ;
A[12] = 20 ; //this is not a syntax error but a logical error

لذا بررسي مرزهاي آرايه بعهده خود برنامه نويس است و بايد از درستي برنامه خود و خارج نشدن از محدوده مجاز مطمئن گردد.

4- مقداردهي اوليه به آرايه هاي يك بعدي بصورت زير انجام مي پذيرد:
int A[3] = {5, 2, 8};

كه در اينجا A[0] برابر 5 ، A[1] برابر 2 و A[2] برابر 8 خواهد شد.
علاوه براين مي توان فقط به تعدادي از عناصر آرايه مقدار داد، دراينصورت مقدار عناصر باقيمانده آرايه اتوماتيك 0 خواهد شد.
int B[10] = {5, 8} ;
در اينجا عناصر B[2] به بعد مقدار 0 خواهند گرفت. بنابراين مي توان براي 0 كردن كليه عناصر يك آرايه به شكل زير عمل كرد :
int C[10] = {0};
چنانچه به آرايه مقدار دهي اوليه كرده باشيم، مي توان تعداد عناصر آرايه را نيز ذكر نكرد، دراينصورت اندازه آرايه بطور اتوماتيك برابر تعداد مقادير مشخص شده خواهد شد.
int C[] = {10, 15, 20};
در مثال فوق آرايه C با 3 عضو درنظر گرفته مي شود.

View Search's Photo Album Search آفلاين است   پاسخ با نقل قول
قدیمی Thursday 27 September 2007, 09:27 PM   #5
سرپرست انجمن
 
Search آواتار ها
 

تاریخ عضویت: January 24th, 2007
نوشته ها: 36,573

سطح دانش: 96 [♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥♥ Bé-Yêu ♥]
سابقه در سایت: 3563 / 3563
قابليت: 12191 / 13550
ميزان تجربه: 1%

Thanks: 69
Thanked 1,388 Times in 1,051 Posts
قدرت اعتبار: 38 Search is on a distinguished road
پیش فرض

ساختارهای کنترلی در زبان c

در فصل ششم اشاره کردیم که در برنامه نویسی ساختیافته، هر برنامه از 3 ساختار کنترلی بنام: ساختار ترتیب، ساختار انتخاب و ساختار تکرار تشکیل می گردد. از آنجا كه اين 3 ساختار، نحوه و ترتيب اجراي برنامه را كنترل مي كنند، به آنها ساختارهاي كنترلي گفته مي شود. تا کنون فقط با برنامه هایی سروکار داشته ایم که از ساختار ترتیب استفاده می کرده اند، چرا که دستورهای زبان C در حالت عادی به همان ترتیبی که نوشته شده اند، یکی پس از دیگری اجرا می شوند.
اما زبان C دارای 3 نوع ساختار انتخاب می باشد که عبا رتند از : ساختار if یا ساختار تک انتخابی، ساختار if / else یا ساختار دو انتخابی و ساختار switch یا ساختار چند انتخابی. علاوه براین، این زبان دارای 3 نوع ساختار تکرار بنامهای while، for و do / while نیز می باشد که هریک را بطور کامل شرح خواهیم داد.
قرارداد: توجه کنید که در هنگام تشریح یک دستور، خود دستور با رنگ آبی و عملگرهای آن مانند () با رنگ قرمز نشان داده می شوند. قسمتهایی که در داخل <> قرار می گیرند، عبارت یا دستوری هستند که باید در هنگام استفاده جایگزین گردند.
ساختار انتخاب if
این دستور به شکل زیر استفاده می شود:
if (<expresion>) <statement>;
نحوه کار بدینصورت است که ابتدا عبارت موجود در قسمت <expression> ارزیابی می شود. در صورتیکه درست ارزیابی گردد، دستور قسمت <statement> اجرا خواهد شد و در صورتیکه نادرست باشد، بدون اینکه دستور قسمت <statement> را اجرا کند به دستور بعدی خواهد رفت. این دستور می تواند بصورت زیر نیز استفاده گردد:
if (<expresion>) <statement 1>;
else <statement 2>;
در اینصورت ابتدا عبارت موجود در قسمت <expression> ارزیابی می شود. در صورتیکه درست ارزیابی گردد، دستور قسمت <statement 1> اجرا خواهد شد، و در صورتیکه نادرست باشد، دستور قسمت <statement 2> اجرا خواهد شد. در هر حال فقط یکی از این دو قسمت اجرا خواهد گردید.
دقت کنید که پرانتز استفاده شده پس از دستور if برخلاف برخی زبانهای دیگر، اجباری است. علاوه براین، در این دستور نیازی به استفاده از then نمی باشد.
بعنوان مثال چنانچه متغیر grade حاوی نمره دانشجو باشد و بخواهیم بر مبنای نمره وی، پیغام مناسبی چاپ کنیم، می توانیم از دستور زیر استفاده کنیم:
if (grade> = 10) printf(“Passed !”);
else printf(“Failed!”);
در حالت عادی دستور if منتظر یک دستور در بدنه خود می باشد، اما چنانچه می خواهید چندین دستور را در بدنه یک دستور if دهید، باید آنها را در داخل آکولاد باز وبسته { } قرار دهید. این مجموع دستورات را یک دستور مرکب می گویند. بطور کلی در زبان C هرجا که می توان یک دستور قرار داد، می توان از یک دستور مرکب نیز استفاده کرد.به یک دستور مرکب، بلوک نیز گفته می شود. بنابراین صورت کلی دستور if به شکل زیر است:
if (<expression>) {
<statement 1> ;
<statement 2> ;
….
<statement n> ;
}
else {
<statement 1> ;
<statement 2> ;
…….
<statement m> ;
}
توجه کنید که وجود قسمت else اختیاری است و در ضمن ممکن است یکی از دو قسمت دارای دستور ساده و دیگری دارای دستور مرکب باشد. بعنوان یک مثال کاملتر به برنامه زیر توجه کنید:
برنامه 1) برنامه ای بنویسید که ضرایب یک معادله درجه 2 را دریافت و ریشه های آن را محاسبه و چاپ نماید.
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
#include <math.h>
void main() {
int a, b, c;
float x1, x2, delta;
clrscr();
printf(“Please enter a, b and c : “);
scanf(“%d %d %d”, &a, &b, &c);
if (a==0) {
printf(“wrong equation!”);
exit(1) ;
}
delta = b*b – 4*a*c;
if (delta <0)
printf(“No answer !”);
else if (delta == 0) {
x1 = -b / (2*a);
printf(“There is one answer, x = %f”,x1);
}
else {
delta = sqrt(delta);
x1 = (-b+delta) / (2*a);
x2 = (-b-delta) / (2*a);
printf(“There are two answers, x1= %4.2f and x2= %4.2f”, x1, x2);
}
}
Please enter a, b and c : 3 -7 2
There is two answers, x1 = 2.00 and x2 = 0.33
چندين نكته درمورد برنامه بالا قابل ذكر است.
1- در اين برنامه از 2 تابع جديد استفاده شده است.اولي تابع sqrt كه يك عدد را به عنوان ورودي دريافت و جذر آن را باز مي گرداند. اين تابع در فايل math.h تعريف شده است. و ديگري تابع exit كه باعث مي شود اجراي برنامه خاتمه يابد. اين تابع نيز در فايل stdlib.h تعريف شده است.
2- به نحوه دندانه گذاري در برنامه دقت كنيد، هرجا كه بلوك جديدي ايجاد شده است، دستورات آن حدود 3 كاراكتر جلوتر نوشته شده اند. اينكار باعث مي شود كه خوانايي برنامه افزايش يابد.
3- توجه كنيد كه همانطور كه قبلا نيز گفته شد، خروجي يك عبارت مقايسه اي، يك عدد است كه 0 نشانه نادرست و هر عدد ديگر نشانه درست است. بنابراين در قسمت شرط يك