صفحه 3 از 7 نخستنخست 1234567 آخرینآخرین
نمایش نتایج: از شماره 21 تا 30 , از مجموع 61

موضوع: ++ C

  1. #21
    مدیر بازنشسته
    تاریخ عضویت
    2008/10/14
    سن
    36
    نوشته ها
    3,180
    سپاس ها
    19
    سپاس شده 582 در 473 پست

    Post نوع داده ای enum

    نوع داده ای enum


    enum يک نوع داده ای تعريف شده توسط برنامه نويس را که به آن نوع داده شمارش می گويند، ايجاد می کند. نحوه ايجاد يک نوع داده شمارش به صورت زير می باشد.

    enum {ثابت n و ... و ثابت 2 و ثابت 1} نام نوع داده
    اين دستور به ترتيب در ثابت 1 ، ثابت 2 و ... و ثابتn اعداد صحيح متوالی 0 تا n را قرار می دهد . به صورت پيش فرض مقداردهی متغيرها در اين دستور از صفر شروع می شود.

    enum TrueFalse {FALSE , TRUE}
    دستور فوق به ثابت FALSE ، عدد صفر و به ثابت TRUE عدد 1 را تخصيص می دهد. حال اگر بخواهيم مقداردهی از عددی غير از صفر شروع شود بايد عدد مورد نظر را مشخص کنيم :

    enum Days {SAT = 1, SUN, MON, TUE, WED, THU, FRI}
    دستور فوق به روزهای هفته به ترتيب اعداد 1 تا 7 را نسبت می دهد. توصيه می شود که نام ثابت های شمارشی را با حروف بزرگ بنويسيد ، بدين صورت اين ثابتها با متغيرهای برنامه ، اشتباه نمی شوند. ضمناً enum را در ابتدای برنامه به کار ببريد.

    در حقيقت اين نوع داده به هر يک از موارد ليستی از اعداد نامی را نسبت می دهد. به عنوان نمونه در مثال روزهای هفته هر يک از اعداد 1 تا 7 را با يکی از روزهای هفته نام گذاری کرديم.

    مقدار دهی موارد ليست به صورت های مختلف امکان پذير می باشد.

    enum Days { MON, TUE, WED, THU, FRI, SAT , SUN = 0}
    دستور فوق SUN را با عدد صفر و SAT را با عدد 1- و ... و MON را با عدد -6 مقدار دهی می کند.

    enum Colors {BLACK = 2, GREEN = 4, RED = 3,
    BLUE = 5, GRAY,WHITE = 0}
    در دستور فوق هر يک از موارد با عدد نسبت داده شده مقدار دهی می شوند و GRAY با عدد 6 مقدار دهی می شود چون بعد از BLUE = 5 آمده است.

    به محض ساخته شدن ليست ، نوع داده نوشته شده توسط برنامه نويس قابل استفاده می گردد و می توان متغيرهايی را از نوع داده نوشته شده توسط برنامه نويس به همان شيوه ای که ساير متغيرها را تعريف می کرديم، تعريف کرد. به عنوان مثال :

    TrueFalse tf1,tf2;
    Days day1, day2 = SUN;
    Colors color1 = BLACK , color2 = GRAY;
    همچنين متغيرها را می توان هنگام ايجاد نوع داده، تعريف کرد. به عنوان مثال :

    TrueFalse {FALSE, TRUE} tf1 ,tf2;
    نکته : تبديل داده ای از نوع enum به عدد صحيح مجاز می باشد ولی بر عکس اين عمل غير مجاز است. به عنوان مثال :

    enum MyEnum {ALPHA, BETA, GAMMA};
    int i = BETA;
    int j = 3+GAMMA;
    دستورات فوق مجاز می باشند، و اين دستورات عدد 1 را در i و 5 را در j قرار می دهند.

    enum MyEnum {ALPHA, BETA, GAMMA};
    MyEnum x = 2;
    MyEnum y = 123;
    ولی دستورات فوق غير مجاز می باشند. البته بعضی از کامپايلرها اين موضوع را ناديده می گيرند و تنها يک پيغام اخطار می دهند ولی توصيه می شود که برای پيشگيری از وقوع خطاهای منطقی در برنامه از به کار بردن دستوراتی مانند کدهای فوق خودداری کنيد.

    برنامه زير نحوه کاربرد نوع داده enum را نشان می دهد.

    #include <iostream.h>
    int main()
    {
    enum PizzaSize{SMALL,MEDIUM,LARGE,EXTRALARGE};
    PizzaSize size;
    size=LARGE;

    cout<<"The small pizza has a value of "<<SMALL;
    cout<<"\nThe medium pizza has a value of "<<MEDIUM;
    cout<<"\nThe large pizza has a value of "<<size;

    return 0;
    }
    خروجی برنامه به صورت زير می باشد:

    The small pizza has a value of 0
    The medium pizza has a value of 1
    The large pizza has a value of 2

  2. کاربر روبرو از پست مفید B@RBOD سپاس کرده است .


  3. #22
    مدیر بازنشسته
    تاریخ عضویت
    2008/10/14
    سن
    36
    نوشته ها
    3,180
    سپاس ها
    19
    سپاس شده 582 در 473 پست

    Post توابع بدون خروجی و آرگومان

    توابع بدون خروجی و آرگومان


    در برنامه نويسی به توابعی نياز پيدا می کنيم که نياز ندارند چيزی را به عنوان خروجی تابع برگردانند و يا توابعی که نياز به آرگومان و ورودی ندارند ويا هر دو. زبان ++C برای امکان استفاده از چنين توابعی، کلمه void را در اختيار ما قرار داده است. اگر بخواهيم تابعی بدون خروجی ايجاد کنيم کافی است به جای نوع داده خروجی تابع کلمه void را قرار دهيم. به تابع زير توجه کنيد.

    void function (int num)
    {
    cout << "My input is" << num << endl;
    }
    همانطور که می بينيد اين تابع نيازی به استفاده از دستور return ندارد چون قرار نيست چيزی را به عنوان خروجی تابع برگرداند. تابع فوق بر اساس مقدار داده ورودی، پيغامی را بر روی صفحه نمايش چاپ می کند.

    حال که با void آشنا شديد می توانيم از اين به بعد تابع main را از نوع void تعريف کنيم. در اين صورت ديگر نيازی به استفاده از دستور return 0;در انتهای برنامه نداريم :

    void main()
    {
    دستورات برنامه
    }
    به عنوان مثال برنامه برج هانوی را که در مبحث توابع بازگشتی نوشتيم با استفاده از نوع void بازنويسی می کنيم.

    #include <iostream.h>

    void hanoi(int, char, char, char);

    void main( )
    {
    cout<<"Moving 4 disks form tower A to C."<<endl;
    hanoi(4,'A','B','C');
    }

    void hanoi(int n, char first, char help, char second) {
    if (n == 1) {
    cout << "Disk " << n << " from tower " << first
    << " to tower " << second << endl;
    } else {
    hanoi(n-1, first, second, help);
    cout << "Disk " << n << " from tower " << first
    << " to tower " << second << endl;
    hanoi(n-1, help, first, second);
    }
    }
    همانطور که در برنامه فوق می بينيد تابع hanoi بدون دستور return نوشته شده است، زيرا نوع تابع void می باشد، يعنی تابع بدون خروجی است و توابع بدون خروجی را می توانيم مستقيماً همانند برنامه فوق فراخوانی کنيد. يعنی کافی است نام تابع را همراه آرگومانهای مورد نظر بنويسيم.

    برای ايجاد توابع بدون آرگومان می توانيد در پرانتز تابع کلمه void را بنويسيد يا اينکه اين پرانتز را خالی گذاشته و در آن چيزی ننويسيد.

    void function1();
    int function2(void);
    در دو دستور فوق تابع function1 از نوع توابع بدون خروجی و بدون آرگومان ايجاد می شود. و تابع function2 از نوع توابع بدون آرگومان و با خروجی از نوع عدد صحيح می باشد، برای آشنايی با نحوه کاربرد توابع بدون آرگومان به برنامه زير توجه کنيد :

    #include <iostream.h>

    int function(void);

    void main( )
    {
    int num, counter = 0;
    float average, sum = 0;

    num=function();

    while (num != -1){
    sum += num ;
    ++counter;
    num=function();
    }

    if (counter != 0){
    average = sum / counter;
    cout << "The average is " << average << endl;
    }
    else
    cout << "No numbers were entered." << endl;
    }

    int function(void){
    int x;
    cout << "Enter a number (-1 to end):";
    cin >>x;
    return x;
    }
    همانطور که در برنامه فوق مشاهده می کنيد تابع function از نوع توابع بدون آرگومان می باشد و دارای خروجی صحيح می باشد. اين تابع در برنامه دو بار فراخوانی شده است و وظيفه اين تابع دريافت متغيری از صفحه کليد و برگرداندن آن متغير به عنوان خروجی تابع می باشدو دستور num=function() عدد دريافت شده از صفحه کليد را در متغير num قرار می دهد اگر به ياد داشته باشيد اين برنامه قبلاً بدون استفاده از تابع در مبحث ساختار تکرار while نوشته بوديم. برای درک بهتر اين برنامه توصيه می شود آن را با برنامه موجود در مبحث ساختار تکرار while مقايسه کنيد، و متوجه خواهيد شد که تابع function ما را از دوباره نويسی بعضی از دستورات بی نياز کرده است و نيز برنامه خلاصه تر و مفهوم تر شده است.

  4. کاربر روبرو از پست مفید B@RBOD سپاس کرده است .


  5. #23
    مدیر بازنشسته
    تاریخ عضویت
    2008/10/14
    سن
    36
    نوشته ها
    3,180
    سپاس ها
    19
    سپاس شده 582 در 473 پست

    Post قوانین حوزه

    قوانین حوزه


    قسمتی از برنامه که در آن متغيری تعريف شده و قابل استفاده می باشد، حوزه آن متغير گفته می شود. در زبان ++C به قسمتی از برنامه که با يک علامت ( } ) شروع شده و با علامت ( { ) به پايان می رسد يک بلوک می گويند. به عنوان مثال هنگامی که متغيری را در يک بلوک تعريف می کنيم، متغير فقط در آن بلوک قابل دسترسی می باشد ولذا حوزه آن متغير بلوکی که در آن تعريف شده است ، می باشد. به مثال زير توجه کنيد :

    #include <iostream.h>

    void main( )
    {
    {
    int x= 1;
    cout << x;
    }
    cout << x;
    }
    اگر برنامه فوق را بنويسيم و بخواهيم اجرا کنيم پيغام خطای Undefined symbol 'x' را دريافت خواهيم کرد ودليل اين امر اين است که متغير x فقط در بلوک درونی تابع main تعريف شده است، لذا در خود تابع قابل دسترسی نمی باشد. در اين مبحث به بررسی حوزه تابع، حوزه فايل و حوزه بلوک می پردازيم.

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

    #include <iostream.h>

    int x=1;
    int f();

    void main( )
    {
    cout << x;
    cout << f();
    cout << x;
    }
    int f(){
    return 2*x;
    }
    متغیر x دارای حوزه فایل می باشد. لذا در تابع main و تابع f قابل استفاده می باشد. خروجی برنامه فوق به صورت زير می باشد.

    121
    متغیری که درون توابع و یا به عنوان آرگومان تابع تعریف می گردد، دارای حوزه تابع می باشد و از نوع متغیرهای محلی است و خارج ازتابع قابل استفاده و دسترسی نمی باشد. توابعی که تا کنون نوشتیم ومتغیرهایی که در آن ها تعریف کردیم، همگی دارای حوزه تابع بودند. ضمنا این متغیرها، هنگامی که برنامه از آن تابع خارج می شود، مقادیر خود را از دست می دهند. حال اگر بخواهیم یک متغیر محلی تابع، مقدار خود را حفظ کرده و برای دفعات بعدی فراخوانی تابع نیز نگه دارد، زبان ++c کلمه static را در اختیار ما قرار داده است. کلمه static را باید قبل از نوع متغیر قرار دهیم. مانند:

    static int x=1;
    دستور فوق متغیر x را از نوع عدد صحیح تعریف می کند و این متغیر با اولین فراخوانی تابع مقدار دهی می شود و در دفعات بعدی فراخوانی تابع مقدار قبلی خود را حفظ می کند. به مثال زیر توجه کنید:

    #include <iostream.h>

    int f();

    void main( )
    {
    cout << f();
    cout << f();
    cout << f();
    }
    int f(){
    static int x=0;
    x++;
    return x;
    }
    خروجی برنامه فوق به صورت زیر می باشد:

    123
    برنامه با اولین فراخوانی تابع f به متغیر محلی x مقدار 0 را می دهد، سپس به x یک واحد اضافه می شود و به عنوان خروجی برگردانده می شود. پس ابتدا عدد1 چاپ می گردد. در بار دوم فراخوانی تابع f ، متغیر x دوباره مقداردهی نمی شود، بلکه به مقدار قبلی آن که عدد 1 است، یک واحد اضافه گشته و به عنوان خروجی برگردانده می شود. پس این بار عدد 2 چاپ می گردد و در نهایت با فراخوانی تابع f برای بار سوم عدد 3 چاپ خواهد شد. اگر برنامه فوق را بدون کلمه static بنويسيم، خروجی 111 خواهد بود.

    یکی از نکاتی که می توان در قوانین حوزه بررسی کرد، متغیرهای همنام در بلوک های تو در تو می باشد. به مثال زیر توجه کنید:

    #include <iostream.h>

    void main( )
    {
    int x=1;
    cout << x;
    {
    int x= 2;
    cout << x;
    }
    cout << x;
    }
    در برنامه فوق متغیر x یک بار در تابع main تعریف شده است و با دیگر در بلوک درونی. خروجی برنامه به صورت زیر می باشد:

    121
    هنگامی که در بلوک درونی متغیری با نام x را مجددا تعریف می کنیم، متغیر خارج از بلوک از دید برنامه پنهان می گردد و تنها متغير داخل بلوک قابل استفاده می شود. همچنین هنگامی که برنامه از بلوک خارج می گردد، متغیر x بیرونی دوباره قابل استفاده می گردد. ضمنا توجه داشته باشید که مقدار متغیر x تابع main تغییری نکرده است، یعنی با وجود استفاده از متغیری همنام و نیز مقداردهی آن، تاثیری روی متغیر x تابع ایجاد نشده است. چون حوزه متغیر x بلوک درونی تنها داخل آن بلوک می باشد.

    برنامه زیر تمام موارد ذکر شده در این مبحث را شامل می شود. بررسی آن و خروجی برنامه شما را در فهم بهتر این مبحث یاری می نماید.

    #include <iostream.h>

    void useLocal( void ); // function prototype
    void useStaticLocal( void ); // function prototype
    void useGlobal( void ); // function prototype

    int x = 1; // global variable

    void main()
    {
    int x = 5; // local variable to main

    cout <<"local x in main's outer scope is "<<x<<endl;

    { // start new scope

    int x = 7;

    cout <<"local x in main's inner scope is "<<x<<endl;

    } // end new scope

    cout <<"local x in main's outer scope is "<<x<< endl;

    useLocal(); //useLocal has local x
    useStaticLocal(); //useStaticLocal has static local x
    useGlobal(); //useGlobal uses global x
    useLocal(); //useLocal reinitializes its local x
    useStaticLocal();//static local x retains its prior value
    useGlobal(); //global x also retains its value

    cout << "\nlocal x in main is " << x << endl;

    } // end main

    //useLocal reinitializes local variable x during each call
    void useLocal( void )
    {
    int x = 25; //initialized each time useLocal is called

    cout << endl << "local x is " << x
    << " on entering useLocal" << endl;
    ++x;
    cout << "local x is " << x
    << " on exiting useLocal" << endl;

    } // end function useLocal

    // useStaticLocal initializes static local variable x
    // only the first time the function is called; value
    // of x is saved between calls to this function
    void useStaticLocal( void )
    {
    // initialized first time useStaticLocal is called.
    static int x = 50;

    cout << endl << "local static x is " << x
    << " on entering useStaticLocal" << endl;
    ++x;
    cout << "local static x is " << x
    << " on exiting useStaticLocal" << endl;

    } // end function useStaticLocal

    // useGlobal modifies global variable x during each call
    void useGlobal( void )
    {
    cout << endl << "global x is " << x
    << " on entering useGlobal" << endl;
    x *= 10;
    cout << "global x is " << x
    << " on exiting useGlobal" << endl;

    } // end function useGlobal
    خروجی برنامه به صورت زیر می باشد:

    local x in main's outer scope is 5
    local x in main's inner scope is 7
    local x in main's outer scope is 5

    local x is 25 on entering useLocal
    local x is 26 on exiting useLocal

    local static x is 50 on entering useStaticLocal
    local static x is 51 on exiting useStaticLocal

    global x is 1 on entering useGlobal
    global x is 10 on exiting useGlobal

    local x is 25 on entering useLocal
    local x is 26 on exiting useLocal

    local static x is 51 on entering useStaticLocal
    local static x is 52 on exiting useStaticLocal

    global x is 10 on entering useGlobal
    global x is 100 on exiting useGlobal

    local x in main is 5
    در برنامه فوق سه تابع با نام های useLocal ,useGlobal ,useStaticLocal داریم. متغیر x تعریف شده در ابتدای برنامه با مقدار 1 به عنوان یک متغیر عمومی می باشد و دارای حوزه فایل است. در تابع main، متغیر x با مقدار 5 تعریف شده است. لذا متغیر عمومی x با مقدار 1 نادیده گرفته می شود و هنگام اجرای دستور cout ، متغير x با مقدار 5 در خروجی چاپ می شود. در بلوک درونی، متغیر x با مقدار 7 تعریف شده است. لذا x عمومی و x محلی تابع main نادیده گرفته می شوند و تنها x با مقدار 7 توسط دستور cout چاپ می گردد. پس از آنکه بلوک حوزه x با مقدار 7 به اتمام می رسد، دوباره x محلی تابع main با مقدار 5 نمایان می گردد.

    تابع useLocal متغیر محلی x را با مقدار 25 در خود تعریف می کند. هنگامی که این تابع در برنامه فراخوانی می شود، تابع ، متغیر x را چاپ می کند، سپس یک واحد به آن اضافه کرده و دوباره x را چاپ می کند. هر بار که این تابع فراخوانی می شود، متغیر x با مقدار 25 در آن تعریف می شود و هنگام خروج از تابع از بین می رود.

    تابع useStaticLocal متغیرمحلی x را از نوع static تعریف کرده و با عدد 50 مقداردهی می کند و سپس آن را چاپ کرده و یک واحد به آن اضافه می کند و دوباره چاپش می کند. اما هنگام خروج از تابع مقدار x از بين نمی رود. و با فراخوانی مجدد تابع ، مقدار قبلی متغير x محلی ، برای اين تابع موجود می باشد و دوباره از نو مقداردهی نمی شود. در اينجا هنگامی که تابع دوباره فراخوانی می شود، x حاوی 51 خواهد بود.

    تابع useGlobal هيچ متغيری را در خود تعريف نمی کند. لذا هنگامی که به متغير x مراجعه می کند ، متغيرx عمومی مورد استفاده قرار می گيرد. هنگامی که اين تابع فراخوانی می شود مقدار متغير x عمومی چاپ می شود. سپس در 10 ضرب شده و دوباره چاپ می گردد. هنگامی که برای بار دوم تابع useGlobal فراخوانی می شود x عمومی حاوی عدد 100 می باشد.

    پس از اينکه برنامه هر يک از توابع فوق را دوبار فراخوانی کرد ، مجددا متغير x تابع main با مقدار 5 چاپ می گردد و اين نشان می دهد که هيچ يک از توابع ، تاثيری روی متغير محلی تابع main نداشتند.

  6. کاربر روبرو از پست مفید B@RBOD سپاس کرده است .


  7. #24
    مدیر بازنشسته
    تاریخ عضویت
    2008/10/14
    سن
    36
    نوشته ها
    3,180
    سپاس ها
    19
    سپاس شده 582 در 473 پست

    Post آرگومانهای پيش فرض توابع

    آرگومانهای پيش فرض توابع


    در برنامه نويسی ممکن است تابعی را به دفعات با آرگومانهای يکسانی صدا بزنيم . در چنين حالتی ، برنامه نويس می تواند برای آرگومانهای تابع ، مقداری را به عنوان پيش فرض قرار دهد . هنگامی که در فراخوانی توابع ، آرگومان دارای مقدار پيش فرض حذف شده باشد ، کامپايلر مقدار پيش فرض آن آرگومان را به تابع خواهد فرستاد .

    آرگومان های پيش فرض بايد سمت راستی ترين آرگومان های تابع باشند . هنگامی که تابعی با بيش از يک آرگومان فراخوانی می شود ، اگر آرگومان حذف شده سمت راستی ترين آرگومان نباشد ، آنگاه همه آرگومانهای سمت راست آن آرگومان نيز بايد حذف شوند . آرگومان های پيش فرض بايد در اولين جايی که نام تابع آورده می شود ( که معمولاً در پيش تعريف تابع است ) مشخص شوند .

    مقادير پيش فرض می توانند اعداد ، مقادير ثابت ، متغيرهای عمومی و يا خروجی تابع ديگر باشند .

    برنامه زير نحوه مقدار دهی به آرگومان های پيش فرض و نيز نحوه فراخوانی تابع با مقدار پيش فرض را نشان می دهد . در اين برنامه حجم جعبه ای محاسبه می شود .

    #include <iostream.h>

    // function prototype that specifies default arguments
    int boxVolume(int length=1, int width=1, int height=1);

    int main()
    {
    //no arguments--use default values for all dimensions
    cout <<"The default box volume is: "<<boxVolume();

    //specify length; default width and height
    cout <<"\n\nThe volume of a box with length 10,\n"
    <<"width 1 and height 1 is: "<<boxVolume(10);

    //specify length and width; default height
    cout <<"\n\nThe volume of a box with length 10,\n"
    <<"width 5 and height 1 is: "<<boxVolume(10,5);

    //specify all arguments
    cout <<"\n\nThe volume of a box with length 10,\n"
    <<"width 5 and height 2 is: "<<boxVolume(10,5,2)
    <<endl;

    return 0; // indicates successful termination

    } //end main

    // function boxVolume calculates the volume of a box
    int boxVolume( int length, int width, int height )
    {
    return length * width * height;
    } // end function boxVolume
    خروجی برنامه فوق به صورت زير می باشد .

    The default box volume is: 1

    The volume of a box with length 10,
    width 1 and height 1 is: 10

    The volume of a box with length 10,
    width 5 and height 1 is: 50

    The volume of a box with length 10,
    width 5 and height 2 is: 100
    در پيش تعريف تابع boxVolume به هر يک از سه آرگومان تابع مقدار پيش فرض 1 داده شده است . توجه داشته باشيد که مقادير پيش فرض بايد در پيش تعريف تابع نوشته شوند ، ضمناً نوشتن نام آرگومان های تابع در پيش تعريف الزامی نيست و در برنامه فوق اينکار تنها برای خوانايی بيشتر انجام گرفته است ، البته توصيه می شود که شما نيز از اين شيوه استفاده کنيد . به عنوان مثال پيش فرض تابع boxVolume در برنامه فوق را می توانستيم به صورت زير نيز بنويسيم :

    int boxVolume (int = 1 , int = 1 , int = 1 );
    در اولين فراخوانی تابع boxVolume در برنامه فوق هيچ آرگومانی به آن داده نشده است لذا هر سه مقدار پيش فرض آرگومان ها مورد استفاده قرار می گيرد و حجم جعبه عدد 1 می شود . در دومين فراخوانی آرگومان length ارسال می گردد ، لذا مقادير پيش فرض آرگومان های width و height استفاده می شوند . در سومين فراخوانی آرگومان های width و length ارسال می گردند لذا مقادير پيش فرض آرگومان height مورد استفاده قرار می گيرد . در آخرين فراخوانی هر سه آرگومان ارسال می شوند لذا از هيچ مقدار پيش فرضی استفاده نمی شود .

    پس هنگامی که يک آرگومان به تابع فرستاده می شود ، آن آرگومان به عنوان length در نظر گرفته می شود و هنگامی که دو آرگومان به تابع boxVolume فرستاده می شود تابع آنها را به ترتيب از سمت چپ به عنوان آرگومان length و سپس width در نظر می گيرد و سرانجام هنگامی که هرسه آرگومان فرستاده می شود به ترتيب از سمت چپ در length و width و height قرار می گيرند .

  8. کاربر روبرو از پست مفید B@RBOD سپاس کرده است .


  9. #25
    مدیر بازنشسته
    تاریخ عضویت
    2008/10/14
    سن
    36
    نوشته ها
    3,180
    سپاس ها
    19
    سپاس شده 582 در 473 پست

    Post عملگر یگانی تفکیک حوزه

    عملگر یگانی تفکیک حوزه


    همانطور که در مبحث قوانين حوزه ديديد تعريف متغيرهای محلی و عمومی با يک نام در برنامه امکان پذير می باشد . زبان ++C عملگر يگانی تفکيک دامنه (::) را برای امکان دستيابی به متغير عمومی همنام با متغير محلی ، در اختيار ما قرار داده است . توجه داشته باشيد که اين عملگر تنها قادر به دستيابی به متغير عمومی در حوزه فايل می باشد . ضمناً متغير عمومی بدون نياز به اين عملگر نيز قابل دستيابی می باشد ؛ به شرط آنکه متغيرمحلی همنام با متغير عمومی ، در برنامه به کار برده نشود . استفاده از عملگر (::) همراه نام متغير عمومی ، در صورتی که نام متغير عمومی برای متغير ديگری به کار برده نشده باشد ، اختياری است . اما توصيه می شود که برای اينکه بدانيد از متغير عمومی استفاده می کنيد از اين عملگر همواره در کنار نام متغير عمومی استفاده کنيد . برنامه زير نحوه کاربرد عملگر (::) را نشان می دهد .

    #include <iostream.h>

    float pi=3.14159;

    void main( )
    {
    int pi=::pi;
    cout << "Local pi is : " << pi << endl;
    cout << "Global pi is : " << ::pi << endl;
    }
    خروجی برنامه به صورت زير می باشد :

    Local pi is : 3
    Global pi is : 3.14159
    در برنامه فوق متغير عمومی pi از نوع float تعريف شده است و در تابع متغير محلی pi از نوع int با مقدار اوليه pi عمومی مقدار دهی می شود . توجه داشته باشيد که برای دستيابی به مقدار pi عمومی از عملگر يگانی تفکيک حوزه (::) استفاده شد . پس از مقدار دهی به pi محلی ، توسط دستور cout ، متغير pi محلی که حاوی عدد 3 است چاپ می گردد و در خط بعدی متغير pi عمومی که حاوی 3.14159 می باشد چاپ خواهد شد .

  10. کاربر روبرو از پست مفید B@RBOD سپاس کرده است .


  11. #26
    مدیر بازنشسته
    تاریخ عضویت
    2008/10/14
    سن
    36
    نوشته ها
    3,180
    سپاس ها
    19
    سپاس شده 582 در 473 پست

    Post ارسال آرگومانها با توابع و ارجاع

    ارسال آرگومانها با توابع و ارجاع


    تا به حال ، در تمام توابعی که نوشتيم آرگومان ها با مقدار به توابع فرستاده می شدند . اين بدان معناست که هنگامی که توابع با آرگومانها فرا خوانی می شدند ، چيزی که ما به عنوان ورودی تابع ارسال می کرديم مقدار يا عدد بود و هرگز خود متغير به تابع فرستاده نشد ، به عنوان مثال تابع maximum در مبحث تعريف توابع را به صورت زير فراخوانی می کنيم :

    int a=5, b=6, c=7, max;
    max = maximum(a,b,c);
    کاری که در اينجا صورت می گيرد فراخوانی تابع و فرستادن مقادير موجود در a وb وc يعنی 5 و 6 و 7 به تابع می باشد . و خود متغيرها فرستاده نمی شوند .


    بدين صورت هنگامی که تابع maximum فراخوانی می شود ، مقدار متغيرهای x وy وz به ترتيب برابر 5 و 6 و 7خواهند شد و هرگونه تغييری روی متغيرهای x وy وz در تابع ، تأثيری روی متغيرهای a وb وc نخواهد داشت . زيرا خود متغيرهای a وb وc به تابع فرستاده نشده اند بلکه مقادير موجود در آنها به تابع ارسال گشته اند .

    در برنامه نويسی مواردی پيش می آيد که بخواهيد از داخل تابع ، مقادير متغيرهای خارجی را تغيير دهيم ، به عنوان مثال در تابع maximum مقدار متغير a را از داخل تابع تغيير دهيم . برای نيل به اين هدف بايد از روش ارسال آرگومان ها با ارجاع استفاده کنيم . برای آنکه آرگومان تابعی با ارجاع فرستاده شود ، کافی است در پيش تعريف تابع بعد از تعيين نوع آرگومان يک علامت (&) بگذاريم و نيز در تعريف تابع قبل از نام آرگومان يک علامت (&) قرار دهيم . برای آشنايی با نحوه ارسال آرگومان ها با ارجاع به برنامه زير توجه کنيد .

    #include <iostream.h>

    void duplicate (int & , int & );

    void main ( )
    {
    int a=1 , b=2 ;
    cout << "a = " << a << " and b = " << b << endl;
    duplicate (a,b);
    cout << "a = " << a << " and b = " << b << endl;
    }

    void duplicate (int &x , int &y)
    {
    x*=2;
    y*=2;
    }
    خروجی برنامه به صورت زير می باشد .

    a = 1 and b = 2
    a = 2 and b = 4
    در برنامه فوق متغيرهای a وb به تابع ارسال می گردند و سپس در دو ضرب می شوند. در اين برنامه مقدار متغيرهای a وb فرستاده نمی شود بلکه خود متغير فرستاده می شود و لذا هنگامی که دستورهای

    x*=2;
    y*=2;
    اجرا می گردند مقادير دو متغيرa وb دو برابر می شود . در حقيقت x وy مانند نام مستعاری برای a وb می باشند .




    هنگامی که متغيری با ارجاع فرستاده می شود هر گونه تغييری که در متغير معادل آن در تابع صورت گيرد عيناً آن تغيير بر روی متغير ارسالی نيز اعمال می گردد .

    مثال : تابعی بنويسيد که دو متغير را به عنوان ورودی دريافت کرده و مقادير آنها را جابه جا کند . از اين تابع در برنامه ای استفاده کنيد .

    #include <iostream.h>
    void change (int & , int &);
    int main ( )
    {
    int a=1 , b=2 ;
    cout << "a is " << a << " and b is " << b << endl;
    change (a,b);
    cout << "a is " << a << " and b is " << b << endl;
    return 0;
    }
    void change (int &x , int &y)
    {
    int temp;
    temp = y;
    y = x;
    x = temp;
    }

    خروجی برنامه به صورت زير است :

    a is 1 and b is 2
    a is 2 and b is 1
    برنامه فوق مقادير دو متغير a وb را توسط change با شيوه ارسال آرگومان با ارجاع جابه جا می کند .

    يکی ديگر از کاربردهای ارسال با ارجاع ، دريافت بيش از يک خروجی از تابع می باشد ، به عنوان مثال تابع prevnext در برنامه زير مقادير صحيح قبل و بعد از اولين آرگومان را به عنوان خروجی بر می گرداند .

    #include <iostream.h>

    void prevnext (int ,int & , int &);

    void main ( )
    {
    int x = 100 , y , z ;
    cout << "The input of prevnext function is "
    << x << endl;
    prevnext (x,y,z) ;
    cout << "previous =" << y <<",Next =" << z;
    }

    void prevnext (int input , int & prev , int & next)
    {
    prev = input - 1 ;
    next = input + 1 ;
    }
    خروجی برنامه فوق به صورت زير می باشد .

    The input of prevnext function is 100
    previous =99,Next =101
    همانطور که مشاهده می کنيد آرگومان input مقدار داده موجود در متغير x را دريافت می کند ولی آرگومان های prev وnext خود متغيرهای y وz را دريافت می کنند . لذا تغييرات روی متغيرprev وnext بر روی y وz انجام می گيرد و توسط تابع مقدار دهی می شوند .

  12. کاربر روبرو از پست مفید B@RBOD سپاس کرده است .


  13. #27
    مدیر بازنشسته
    تاریخ عضویت
    2008/10/14
    سن
    36
    نوشته ها
    3,180
    سپاس ها
    19
    سپاس شده 582 در 473 پست

    Post گرانبار کردن توابع (استفاده از يک نام برای چند تابع)

    گرانبار کردن توابع (استفاده از يک نام برای چند تابع)


    ++C استفاده از يک نام را برای چند تابع ، هنگامی که توابع از نظر نوع آرگومان ها ، تعداد آرگومان ها يا ترتيب قرار گرفتن نوع آرگومان ها با هم متفاوت باشند را امکان پذير کرده است اين قابليت ، گرانبار کردن توابع ناميده می شود . هنگامی که يک تابع گرانبار شده فراخوانی می شود کامپايلر با مقايسه نوع ، تعداد و ترتيب آرگومان ها تابع درست را انتخاب می کند . معمولاً از توابع گرانبار شده برای ايجاد چند تابع با نامهای يکسان که کار يکسانی را بر روی انواع داده ای متفاوتی انجام می دهند استفاده می شود . به عنوان مثال اکثر توابع رياضی زبان ++C برای انواع داده ای متفاوت گرانبار شده اند . گرانبار کردن توابعی که کار يکسانی را انجام می دهند برنامه را قابل فهم تر و خواناتر می سازد . برنامه زير نحوه به کار گيری توابع گرانبار شده را نشان می دهد .

    #include <iostream.h>

    int square( int );
    double square( double );

    void main()
    {
    // calls int version
    int intResult = square( 7 );
    // calls double version
    double doubleResult = square( 7.5 );

    cout << "\nThe square of integer 7 is "
    << intResult
    << "\nThe square of double 7.5 is "
    << doubleResult
    << endl;

    } // end main

    // function square for int values
    int square( int x )
    {
    cout <<"Called square with int argument: "
    << x << endl;
    return x * x;
    } // end int version of function square

    // function square for double values
    double square( double y )
    {
    cout <<"Called square with double argument: "
    << y << endl;
    return y * y;
    } // end double version of function square


    خروجی برنامه به صورت زير می باشد .

    Called square with int argument: 7
    Called square with double argument: 7.5

    The square of integer 7 is 49
    The square of double 7.5 is 56.25
    برنامه فوق برای محاسبه مربع يک عدد صحيح (int) و يک عدد اعشاری (double) از تابع گرانبارشده square استفاده می کند .هنگامی که دستور:

    int intResult = square (7) ;
    اجرا می گردد تابع square با پيش تعريف :

    int square (int) ;
    فراخوانی می شود و هنگامی که دستور :

    double doubleResult = square (7.5) ;
    اجرا می گردد تابع square با پيش تعريف :

    double square (double );
    فراخوانی می شود .

    نکته : توجه داشته باشيد که توابع گرانبار شده الزامی ندارند که وظيفه يکسانی را انجام دهند . و ممکن است کاملاً با هم تفاوت داشته باشند ، ولی توصيه می شود که توابعی را گرانبار کنيد که يک کار را انجام می دهند .

  14. کاربر روبرو از پست مفید B@RBOD سپاس کرده است .


  15. #28
    مدیر بازنشسته
    تاریخ عضویت
    2008/10/14
    سن
    36
    نوشته ها
    3,180
    سپاس ها
    19
    سپاس شده 582 در 473 پست

    Post اعلان آرایه ها

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

    طول آرايه] نام آرايه نوع داده آرايه];
    به عنوان مثال دستور زير آرايه ای به طول 6 ، با نام num را از نوع int ايجاد می کند .

    int num [6];
    توجه داشته باشيد که تمام عناصر دارای نام يکسانی می باشند و تنها با انديس از هم تفکيک می شوند . به عنوان مثال عنصر با انديس 2 دارای مقدار 23560- می باشد ، ضمناً انديس عناصر از 0 شروع می شود .

    استفاده از يک عبارت محاسباتی به جای انديس عناصر امکان پذير می باشد ، به عنوان مثال با فرض اينکه متغير a حاوی 2 و متغير b حاوی 3 باشد ، دستور زير:

    num [a+b] + = 3;
    سه واحد به عنصر num [5] اضافه خواهد کرد و اين عنصر حاوی عدد 3 می گردد . برای چاپ مجموع سه عنصر اول آرايه می توانيد از دستور زير استفاده کنيد :

    cout << num[0] + num[1] + num[2] << endl;
    برای تقسيم عنصر چهارم آرايه بر 2 و قرار دادن حاصل در متغير x از دستور زير می توانيد استفاده کنيد :

    x = num[3]/2;
    نکته : توجه داشته باشيد که عنصر چهارم آرايه با عنصر شماره چهار ( با انديس چهار ) متفاوت می باشد . همانطور که در دستور فوق ديديد عنصر شماره چهار دارای انديس سه می باشد ، دليل اين امر اينست که انديس گذاری از صفر شروع می شود . در آرايه فوق عنصر چهارم آرايه num[3]=-50 می باشد ولی عنصر شماره چهار ( با انديس چهار ) num[4]=32500 می باشد .

    همانند متغيرها چند آرايه را نيز می توان توسط يک دستور تعريف کرد :

    int b[100] , x[27] ;
    دستور فوق 100 خانه از نوع عدد صحيح را برای آرايه با نام b و 27 خانه از نوع عدد صحيح را برای آرايه با نام x در نظر می گيرد .

    برای مقدار دهی اوليه به هر يک از عناصر آرايه می توانيد از شيوه زير استفاده کنيد :

    int n[5] = {32 , 27 , 64 , 18 , 95 }


    اگر طول آرايه هنگام تعريف آرايه تعيين نشده باشد و ليست مقدار عناصر نوشته شود ، همانند دستور زير :

    int n[] = { 1 , 2 , 3 , 4 , 5 }
    در اين صورت کامپايلر به تعداد عناصر ليست ، خانه حافظه برای آرايه در نظر می گيرد ، مثلاً در دستور فوق 5 خانه حافظه برای آرايه n در نظر گرفته می شود .

    راه ديگری که برای مقدار دهی اوليه به عناصر آرايه وجود دارد استفاده از روش زير است :

    int num[10] = {0}
    دستور فوق 10 خانه حافظه برای آرايه num در نظر می گيرد و مقادير همه آنها را صفر می کند . توجه داشته باشيد که اگر از دستور زير استفاده کنيم :

    int num[10] = {1}
    تمامی عناصر مقدار 1 را نمی گيرند بلکه عنصر اول آرايه يک می شود و بقيه عناصر مقدار صفر را می گيرند .

    در تعريف آرايه ديديد که طول آرايه را با عدد صحيح ثابتی تعيين می کنيم . هر جا که از عدد ثابتی استفاده می شود ، متغير ثابت نيز می توان به کار برد . متغيرهای ثابت به صورت زير تعريف می شوند :

    const مقدار متغير = نام متغير ثابت نوع داده متغير ;
    به عنوان مثال :

    const int arraySize = 10;
    دستور فوق عدد 10 را به متغير arraySize ثابت انتساب می دهد . توجه داشته باشيد که مقدار يک متغير ثابت را در طول برنامه نمی توان تغيير داد و نيز متغير ثابت در هنگام تعريف شدن ، مقدار اوليه اش نيز بايد تعيين گردد . به متغيرهای ثابت ، متغيرهای فقط خواندنی نيز گفته می شود . کلمه "متغير ثابت" يک کلمه مرکب ضد و نقيض می باشد چون کلمه متغير متضاد ثابت می باشد و اين اصطلاحی است که برای اينگونه متغيرهای در اکثر زبانهای برنامه نويسی به کار می رود . برنامه زير نحوه تعريف يک متغير ثابت را نشان می دهد :

    #include <iostream.h>

    void main()
    {
    const int x = 7;

    cout << "The value of constant variable x is: "
    << x << endl;

    }
    برنامه فوق عدد 7 را در متغير ثابت x قرار می دهد و توسط دستور cout آنرا چاپ می کند . همانطور که گفتيم مقدار متغير ثابت در هنگام تعريف بايد تعيين گردد و نيز ثابت قابل تغيير نمی باشد ، به برنامه زير توجه کنيد .

    #include <iostream.h>

    void main()
    {
    const int x;

    x=7;
    }
    برنامه فوق هنگام کامپايل شدن دو پيغام خطا خواهد داد ، چون متغير ثابت هنگام تعريف مقدار دهی نشده و نيز در برنامه دستوری برای تغيير مقدار آن آورده نشده است .

    Compiling C:\TCP\BIN\CONST1.CPP:
    Error : Constant variable 'x' must be initialized
    Error : Cannot modify a const object
    مثال : در برنامه زير طول آرايه توسط متغير ثابتی تعيين می گردد و عناصر آرايه توسط حلقه for مقدار دهی شده و سپس توسط حلقه for ديگری ، مقدار عناصر آرايه چاپ می گردد .

    #include <iostream.h>

    void main()
    {
    const int arraySize = 10;

    int s[ arraySize ];

    for ( int i = 0; i < arraySize; i++ )
    s[ i ] = 2 + 2 * i;

    cout << "Element Value" << endl;

    for ( int j = 0; j < arraySize; j++ )
    cout << j << "\t " << s[ j ] << endl;

    }
    خروجی برنامه فوق به صورت زير می باشد :

    Element Value
    0 2
    1 4
    2 6
    3 8
    4 10
    5 12
    6 14
    7 16
    8 18
    9 20

  16. کاربر روبرو از پست مفید B@RBOD سپاس کرده است .


  17. #29
    مدیر بازنشسته
    تاریخ عضویت
    2008/10/14
    سن
    36
    نوشته ها
    3,180
    سپاس ها
    19
    سپاس شده 582 در 473 پست

    Post چند مثال از آرایه ها

    چند مثال از آرایه ها


    مثال : برنامه ای بنويسيد که 10 عدد صحيح را ورودی دريافت کرده و در آرايه ای قرار داده سپس مجموع عناصر آرايه را محاسبه کرده و درخروجی چاپ نمايد .

    #include <iostream.h>

    void main()
    {
    const int arraySize = 10;
    int total = 0,i;
    int a[ arraySize ];

    for (i = 0; i < arraySize; i++)
    {
    cout << "Enter number " << i << " : ";
    cin >> a[ i ];
    }

    for (i = 0; i < arraySize; i++ )
    total += a[ i ];

    cout << "Total of array element values is "
    << total << endl;

    }
    خروجی برنامه به صورت زير می باشد :

    Enter number 0 : 12
    Enter number 1 : 3
    Enter number 2 : 4
    Enter number 3 : 654
    Enter number 4 : 34
    Enter number 5 : 2
    Enter number 6 : 123
    Enter number 7 : 794
    Enter number 8 : 365
    Enter number 9 : 23
    Total of array element values is 2014
    مثال : برنامه ای بنويسيد که توسط آرايه ، نمودار ميله ای افقی برای اعداد {1 و17 و5 و13 و9 و11 و7 و15 و3 و19 } رسم کند .

    #include <iostream.h>

    int main()
    {
    const int arraySize = 10;
    int n[ arraySize ] = { 19, 3, 15, 7, 11,
    9, 13, 5, 17, 1 };

    cout << "Element" << " Value" << endl;

    for ( int i = 0; i < arraySize; i++ ) {
    cout << i << "\t " << n[ i ] << "\t";

    for ( int j = 0; j < n[ i ]; j++ )
    cout << '*';
    cout << endl;
    }

    return 0;

    }
    خروجی برنامه به صورت زير می باشد :


    Element Value
    0 19 *******************
    1 3 ***
    2 15 ***************
    3 7 *******
    4 11 ***********
    5 9 *********
    6 13 *************
    7 5 *****
    8 17 *****************
    9 1 *
    مثال : برنامه ای بنويسيد که يک تاس را 6000 بار پرتاب کرده و توسط آرايه ای تعداد دفعات آمدن هر وجه را حساب کند .( تعداد دفعات آمدن هر وجه را يک عنصر آرايه ای در نظر بگيريد )

    #include <iostream.h>
    #include <stdlib.h>
    #include <time.h>

    void main()
    {
    const int arraySize = 7;
    int frequency[ arraySize ] = { 0 };

    srand( time( 0 ) );

    for ( int roll = 1; roll <= 6000; roll++ )
    ++frequency[ 1 + rand() % 6 ];

    cout << "Face Frequency" << endl;

    for ( int face = 1; face < arraySize; face++ )
    cout << face << "\t" << frequency[face] << endl;

    }
    خروجی برنامه به صورت زير می باشد :


    Face Frequency
    1 1023
    2 990
    3 1008
    4 971
    5 1025
    6 983
    دستور ++frequency [rand()%6 + 1]; ، مقدار عنصر مربوط به هر وجه را يک واحد اضافه می کند ، زيرا rand()%6 + 1 عددی بين 1 تا 6 توليد می کند ، پس هر بار به طور تصادفی تنها مقدار عنصر مربوط به يکی از وجوه افزايش می يابد .

    يکی از کار برد های آرايه ها ، استفاده از آنها برای ذخيره رشته ای از حروف می باشد . تا به حال متغيرهايی که از ورودی دريافت می کرديم و يا آرايه هايی که تا به اينجا ديديد تنها شامل اعداد می شدند در اينجا به عنوان مثال نحوه دريافت يک نام از ورودی و چاپ آن در خروجی را بررسی می کنيم .(در فصل بعد يعنی اشاره گرها و رشته ها ، به طور مفصل تر راجع به رشته ها صحبت خواهم کرد )

    يک عبارت رشته ای مانند: "hello" در واقع آرايه ای از حروف می باشد.

    char string1[]="hello";
    دستور فوق آرايه ای به نام string1 را با کلمه hello مقدار دهی می کند. طول آرايه فوق برابر است با طول کلمه hello يعنی 5 بعلاوه يک واحد که مربوط است به کاراکتر پوچ که انتهای رشته را مشخص می کند. لذا آرايه string1 دارای طول 6 می باشد. کاراکتر پوچ در زبان ++C توسط '\0' مشخص می گردد. انتهای کليه عبارات رشته ای با اين کاراکتر مشخص می شود.

    char string1[]={'h','e','l','l','o','\0'}
    دستور فوق عناصر آرايه string1 را جداگانه مقدار دهی می کند. توجه داشته باشيد که عناصر آرايه در دستور فوق داخل (') قرار گرفتند و نيز انتهای رشته با '\0' تعيين شد. نتيجه همانند دستور char string1[]="hello"; می باشد.

    چون عبارت رشته ای، آرايه ای از حروف می باشند، لذا به هر يک از حروف رشته، توسط انديس عنصری که شامل آن حرف می باشد، می توان دسترسی پيدا کرد. به عنوان مثال string1[0] شامل 'h' و string1[3] شامل 'l' و string1[5] شامل '\0' می باشد.

    توسط دستور cin نيز می توان به طور مستقيم کلمه وارد شده از صفحه کليد را در آرايه ای رشته ای قرار داد.

    char string2[20];
    دستور فوق يک آرايه رشته ای که قابليت دريافت کلمه ای با طول 19 به همراه کاراکتر پوچ را دارا می باشد.

    cin >> string2;
    دستور فوق رشته ای از حروف را از صفحه کليد خوانده و در string2 قرار می دهدو کاراکتر پوچ را به انتهای رشته وارد شده توسط کاربر اضافه می کند. به طور پيش فرض دستور cin کاراکتر ها را از صفحه کليد تا رسيدن به اولين فضای خالی در يافت می کند. به عنوان مثال اگر هنگام اجرای دستور cin >> string2; کاربر عبارت "hello there" را وارد کند، تنها کلمه hello در string2 قرار می گيرد. چون عبارت وارد شده شامل کاراکتر فاصله است. برنامه زير نحوه به کار گيری آرايه های رشته ای را نشان می دهد.

    #include <iostream.h>

    void main()
    {
    char name[ 20 ];

    cout << "Please Enter your name : ";
    cin >> name;

    cout << "Welcome, " << name
    << " to this program. \n" ;

    cout << "Your separated name is\n";

    for ( int i = 0; name[ i ] != '\0'; i++ )
    cout << name[ i ] << ' ';

    }
    خروجی برنامه به صورت زير می باشد :


    Please Enter your name : Mohammad
    Welcome, Mohammad to this program.
    Your separated name is
    M o h a m m a d
    در برنامه فوق حلقه for ، حروف نام وارد شده توسط کاربر را جدا جدا در خروجی چاپ می کند. ضمنا شرط حلقه name[ i ] != '\0' می باشد و تا وقتی اين شرط برقرار است که حلقه به انتهای رشته نرسيده باشد.

    در مبحث قوانين حوزه ديديد که اگر بخواهيم يک متغير محلی تابع، مقدار خود را حفظ کرده و برای دفعات بعدی فراخوانی تابع نيز نگه دارد، از کلمه static استفاده کرديم. نوع static را برای آرايه ها نيز می توان به کار برد و از همان قوانين گفته شده در مبحث مذکور پيروی می کند. به برنامه زير و خروجی آن توجه کنيد.

    #include <iostream.h>

    void staticArrayInit( void );
    void automaticArrayInit( void );

    int main()
    {
    cout << "First call to each function:\n";
    staticArrayInit();
    automaticArrayInit();

    cout << "\n\nSecond call to each function:\n";

    staticArrayInit();
    automaticArrayInit();
    cout << endl;

    return 0;

    }

    // function to demonstrate a static local array
    void staticArrayInit( void )
    {
    // initializes elements to 0
    // first time function is called
    static int array1[ 3 ]={0};

    cout << "\nValues on entering staticArrayInit:\n";

    // output contents of array1
    for ( int i = 0; i < 3; i++ )
    cout << "array1[" << i << "] = "
    << array1[ i ] << " ";

    cout << "\nValues on exiting staticArrayInit:\n";

    // modify and output contents of array1
    for ( int j = 0; j < 3; j++ )
    cout << "array1[" << j << "] = "
    << ( array1[ j ] += 5 ) << " ";

    } // end function staticArrayInit

    // function to demonstrate an automatic local array
    void automaticArrayInit( void )
    {
    // initializes elements each time function is called
    int array2[ 3 ] = { 1, 2, 3 };

    cout << endl << endl;
    cout << "Values on entering automaticArrayInit:\n";

    // output contents of array2
    for ( int i = 0; i < 3; i++ )
    cout << "array2[" << i << "] = "
    << array2[ i ] << " ";

    cout << "\nValues on exiting automaticArrayInit:\n";

    // modify and output contents of array2
    for ( int j = 0; j < 3; j++ )
    cout << "array2[" << j << "] = "
    << ( array2[ j ] += 5 ) << " ";

    }
    خروجی برنامه به صورت زير می باشد :


    First call to each function:

    Values on entering staticArrayInit:
    array1[0] = 0 array1[1] = 0 array1[2] = 0
    Values on exiting staticArrayInit:
    array1[0] = 5 array1[1] = 5 array1[2] = 5

    Values on entering automaticArrayInit:
    array2[0] = 1 array2[1] = 2 array2[2] = 3
    Values on exiting automaticArrayInit:
    array2[0] = 6 array2[1] = 7 array2[2] = 8

    Second call to each function:

    Values on entering staticArrayInit:
    array1[0] = 5 array1[1] = 5 array1[2] = 5
    Values on exiting staticArrayInit:
    array1[0] = 10 array1[1] = 10 array1[2] = 10

    Values on entering automaticArrayInit:
    array2[0] = 1 array2[1] = 2 array2[2] = 3
    Values on exiting automaticArrayInit:
    array2[0] = 6 array2[1] = 7 array2[2] = 8
    در برنامه فوق عناصر آرايه array1 در اولين بار فراخوانی تابع staticArrayInit مقدار صفر را می گيرند ولی در دفعات بعدی فراخوانی اين تابع، آخرين مقدار قبلی خود را حفظ می کنند . اما آرايه array2 در هر بار فراخوانی تابع automaticArrayInit مقدار دهی اوليه می شود و با خروج از تابع مقدار خود را از دست می دهد.

  18. کاربر روبرو از پست مفید B@RBOD سپاس کرده است .


  19. #30
    مدیر بازنشسته
    تاریخ عضویت
    2008/10/14
    سن
    36
    نوشته ها
    3,180
    سپاس ها
    19
    سپاس شده 582 در 473 پست

    Post ارسال آرایه ها به توابع

    برای ارسال يک آرايه به عنوان آرگومان به يک تابع ، کافيست نام آرايه را بدون علامت براکت ([]) به کار ببريد . به عنوان مثال اگر آرايه ای با نام x به صورت زير تعريف شده باشد :

    int x[24];
    برای ارسال آن به تابع modifyArray کافيست تابع را به صورت زير:

    modifyArray(x,24);
    فراخوانی کنيد . دستور فوق آرايه و طول آن را به تابع modifyArray ارسال می کند . معمولاً هنگامی که آرايه ای را به تابعی ارسال می کنند ، طول آرايه را نيز همراه آرايه به عنوان يک آرگومان جداگانه به تابع می فرستند.

    ++C آرايه ها را با شيوه شبيه سازی شده ارسال آرگومان ها با ارجاع به تابع ارسال می نمايد ، لذا تابع فراخوانی شده مقدار عناصر آرايه ارسالی را می تواند تغيير دهد . هنگامی که نام تابع را به عنوان آرگومان تابع به کار می بريم ، آدرس خانه حافظه اولين عنصر آرايه به تابع ارسال می شود لذا تابع می داند که عناصر آرايه در کجای حافظه قرار گرفته اند . بنابراين هنگامی که تابع فراخوانی شده عناصر آرايه را تغيير می دهد ، اين تغييرات روی عناصر آرايه اصلی که به تابع ارسال شده است ، انجام می پذيرد .

    نکته : توجه داشته باشيد که عناصر آرايه را به صورت جداگانه همانند ارسال متغيرها و يا مقادير عددی به تابع ارسال کرد . در اين صورت تغيير بر روی آرگومان ارسالی ، تأثيری بر روی عنصر آرايه نخواهد داشت . در حقيقت اين شيوه ، همان ارسال با مقدار می باشد .

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

    void modifyArray (int b[] ,int array size)
    دستور فوق مشخص می کند که تابع modifyArray قادر به دريافت آدرس آرايه ای از اعداد صحيح توسط آرگومان b و تعداد عناصر آرايه توسط آرگومان arraySize می باشد . ضمناً تعداد عناصر آرايه را لازم نيست بين براکت ها ([]) بنويسيد ، اگر اين کار نيز صورت پذيرد ، کامپايلر آن را ناديده می گيرد . توجه داشته باشيد که پيش تعريف تابع فوق را به صورت زير بنويسيد :

    void modifyArray (int [] , int);
    برنامه زير نحوه ارسال يک آرايه را به تابع و تفاوت ارسال يک عنصر آرايه به تابع و ارسال کل آرايه به تابع را نشان می دهد .

    #include <iostream.h>

    void modifyArray( int [], int );
    void modifyElement( int );

    void main()
    {
    const int arraySize = 5;
    int a[ arraySize ] = { 0, 1, 2, 3, 4 };

    cout<<"Effects of passing entire array by reference:"
    <<"\n\nThe values of the original array are:\n";

    // output original array
    for ( int i = 0; i < arraySize; i++ )
    cout << "\t"<< a[ i ];

    cout << endl;

    // pass array a to modifyArray by reference
    modifyArray( a, arraySize );

    cout << "The values of the modified array are:\n";

    // output modified array
    for ( int j = 0; j < arraySize; j++ )
    cout << "\t" << a[ j ];

    // output value of a[ 3 ]
    cout<<"\n\n\n"
    <<"Effects of passing array element by value:"
    <<"\n\nThe value of a[3] is " << a[ 3 ] << '\n';

    // pass array element a[ 3 ] by value
    modifyElement( a[ 3 ] );

    // output value of a[ 3 ]
    cout << "The value of a[3] is " << a[ 3 ] << endl;

    }

    // in function modifyArray, "b" points to
    // the original array "a" in memory
    void modifyArray( int b[], int sizeOfArray )
    {
    // multiply each array element by 2
    for ( int k = 0; k < sizeOfArray; k++ )
    b[ k ] *= 2;
    }

    // in function modifyElement, "e" is a local copy of
    // array element a[ 3 ] passed from main
    void modifyElement( int e )
    {
    // multiply parameter by 2
    cout << "Value in modifyElement is "
    << ( e *= 2 ) << endl;
    }
    خروجی برنامه فوق به صورت زير می باشد :

    Effects of passing entire array by reference:

    The values of the original array are:
    0 1 2 3 4
    The values of the modified array are:
    0 2 4 6 8


    Effects of passing array element by value:

    The value of a[3] is 6
    Value in modifyElement is 12
    The value of a[3] is 6
    در برنامه فوق ، تابع modifyArray مقدار عناصر آرايه a را که به آن فرستاده شده است دو برابر می کند . تابع modifyElement مقدار آرگومان دريافتی را دو برابر کرده و در خروجی چاپ می کند ولی تأثيری در نسخه اصلی عنصر آرايه نداشته و تغييری در مقدار آن ايجاد نمی کند .

    بعضی مواقع ممکن است بخواهيد که تابعی ، اجازه تغيير عناصر آرايه ای که به آن فرستاده شده است را نداشته باشد . برای اين کار هنگام تعريف تابع کافی است از کلمه const قبل از آرگومان مربوط به آن آرايه استفاده کنيد ، در چنين حالتی اگر داخل تابع قصد تغيير مقدار عناصر آرايه را داشته باشيد با يک پيغام خطای کامپايلر مواجه می شويد و کامپايلر اجازه اين کار را به شما نمی دهد . به برنامه زير توجه کنيد :

    #include <iostream.h>

    void tryToModifyArray( const int [] );

    void main()
    {
    int a[] = { 10, 20, 30 };

    tryToModifyArray( a );

    cout << a[0] <<' '<< a[1] <<' '<< a[2] <<'\n';

    }

    // In function tryToModifyArray, "b" cannot be used
    // to modify the original array "a" in main.
    void tryToModifyArray( const int b[] )
    {
    b[ 0 ] /= 2; // error
    b[ 1 ] /= 2; // error
    b[ 2 ] /= 2; // error
    }


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

    Error in line 19: Cannot modify a const object
    Error in line 20: Cannot modify a const object
    Error in line 21: Cannot modify a const object

  20. کاربر روبرو از پست مفید B@RBOD سپاس کرده است .


صفحه 3 از 7 نخستنخست 1234567 آخرینآخرین

مجوز های ارسال و ویرایش

  • شما نمیتوانید موضوع جدیدی ارسال کنید
  • شما امکان ارسال پاسخ را ندارید
  • شما نمیتوانید فایل پیوست کنید.
  • شما نمیتوانید پست های خود را ویرایش کنید
  •