Skip to content

মডিউল ১৪ঃ ফাংশন

মডিউল ১৪-০ঃ সূচনা

প্রোগ্রামিং এ ফাংশন খুবই ইম্পর্ট্যান্ট একটা কন্সেপ্ট। ধীরে ধীরে এটার আরো বিস্তারিত ইউস দেখতে পাবে। আজকে দেখানো হবে ফাংশনের বেসিক কিছু কন্সেপ্ট। যেমন ফাংশন কি, কেন আমরা এটা ইউস করবো। কিভাবে ডিক্লেয়ার করতে হয়। সাথে কয়েক টাইপের ফাংশনের সাথেও তোমাদের পরিচয় করিয়ে দেওয়া হবে।


মডিউল ১৪-১ঃ What is Function

ফাংশনকে আমরা একটি রোবট এর মতো চিন্তা করতে পারি। এই ফাংশনকে কিছু ইন্সট্রাকশন এবং ইনপুট দেওয়া হলে ফাংশন সেই অনুযায়ী কাজ করে আউটপুট রিটার্ন করতে পারে। আমাদের যদি কোডে কোন কাজ বারবার করতে হয় তাহলে আমরা সেই কাজটি একটি ফাংশনের মধ্যে লিখে রাখতে পারি। তাহলে যখনি আমরা সেই ফাংশনকে কল করব তখনি সেই কাজটি ফাংশন আমাকে করে আউটপুট রিটার্ন করে দিবে। তাহলে আমাদেরকে ওই কাজটি করার কোড বারবার লিখতে হবে না।

সি প্রোগ্রামিং এ একটি ফাংশনের রিটার্ন টাইপ থাকে। ফাংশনটি কোন টাইপের ডাটা রিটার্ন করবে তা বলা থাকে রিটার্ন টাইপে। ফাংশনের একটি ইউনিক ভেলিড নাম থাকে। একটি সি কোডে আমরা যেমন একই নামের ভেরিয়েবল দুইবার ডিক্লেয়ার করতে পারি না, প্রতিটি ভেরিয়েবল এর নাম ইউনিক হতে হয়। ফাংশন এর নামও ঠিক তেমনি ইউনিক হতে হয়। তারপর ফাংশনে কিছু প্যারামিটার থাকে। যেখানে আমরা ফাংশনের ইনপুটগুলো দেই ভেরিয়েবল হিসেবে।

ফাংশন লিখতে হয় মেইন ফাংশনের উপরে। মেইন ফাংশনের নিচেও লিখা যায় কিন্তু সেক্ষেত্রে মেইন ফাংশনের উপরে ফাংশনটি ডিক্লেয়ার করে আসতে হয়।

সি প্রোগ্রামিং এ একটি ফাংশন ডিক্লেয়ার করার সিন্টেক্সঃ

return_type function_name ( parameters )
{
    // code
    return statement;
}

ফাংশনটি যদি কোন কিছু রিটার্ন না করে তাহলে সেটির রিটার্ন টাইপ হিসেবে void লিখা হয়। যদি কোন প্যারামিটার না থাকে তাহলে প্যারামিটার এর জায়গাটি ফাঁকা রাখা যায় অথবা void লিখে রাখা যায়। যদি ফাঁকা থাকে তাহলে জোর করে প্যারামিটার দেওয়া হলেও সেটি ইগনোর করবে আর void লিখা থাকলে প্যারামিটার দেওয়া হলে এরোর দিবে।

এবার আমরা দুটি সংখ্যা যোগ করি ফাংশন ব্যাবহার করেঃ

Code (Function Declaration):

c
#include <stdio.h>

int add(int a, int b) // ফাংশন ডিক্লেয়ার করা হয়েছে যার নাম add, প্যারামিটার হিসেবে দুটি সংখ্যা নেওয়া হচ্ছে, তাই প্যারামিটারে দুটি int ভেরিয়েবল ডিক্লেয়ার করা হচ্ছে। এই ফাংশনটি প্যারামিটার হিসেবে নেওয়া দুটি সংখ্যা যোগ করে যোগফল রিটার্ন করবে তাই এটির রিটার্ন টাইপ হচ্ছে int
{
    int ans = a+b; // প্যারামিটার হিসেবে নেওয়া দুটি সংখ্যা যোগ করে যোগফলটি একটি ভেরিয়েবলে স্টোর করে রাখা হচ্ছে।
    return ans; // যোগফলটি রিটার্ন করে দেওয়া হচ্ছে।
}

Code (Function Call in main):

c
int main()
{
    int a,b;
    scanf("%d %d", &a, &b); // দুটি সংখ্যা ইনপুট নেওয়া হচ্ছে।
    int sum = add(a, b); // add ফাংশনকে কল করা হচ্ছে এবং প্যারামিটার হিসেবে ইনপুট নেওয়া দুটি সংখ্যা দিয়ে দেওয়া হচ্ছে। ফাংশনটি কল করার পর যা রিটার্ন করবে তা sum ভেরিয়েবলে স্টোর করা হচ্ছে।
    printf("sum = %d", sum); // sum ভেরিয়েবলটি প্রিন্ট করা হচ্ছে যেটিতে দুটি সংখ্যার যোগফল স্টোর রয়েছে।
}

এখানে আমরা যোগ করার জন্য একটি ফাংশন লিখেছি। যেটি ইনপুট হিসেবে দুটি সংখ্যা নিবে। তারপর তাতে সেই দুটি সংখ্যা যোগ করার ইন্সট্রাকশন দেওয়া হয়েছে। যোগ শেষে যোগফলটি রিটার্ন করে দিবে। এই ফাংশনকে কল করে যেকোন দুটি সংখ্যা দেওয়া হলে সে তাদের যোগফল রিটার্ন করবে। এভাবে করে আমরা যেকোন ইন্সট্রাকশন দিয়ে ফাংশন লিখতে পারি।

ফাংশন মূলত ৪ প্রকার হয়ঃ

১। রিটার্ন + প্যারামিটার

২। রিটার্ন + নো প্যারামিটার

৩। নো রিটার্ন + প্যারামিটার

৪। নো রিটার্ন + নো প্যারামিটার


মডিউল ১৪-২+১৪-৩ঃ রিটার্ন + প্যারামিটার

এই টাইপের ফাংশনে রিটার্ন ও থাকে প্যারামিটার ও থাকে। এই টাইপ ফাংশন এর উদাহরন আমরা পূর্বের আর্টিকেলে দেখেছি।

Code:

c
#include <stdio.h>
int sum(int x, int y)   // রিটার্ন এবং প্যারামিটার দুটোই আছে। প্যারামিটার হিসেবে দুটো সংখ্যা নিয়ে তাদের যোগফল রিটার্ন করা হচ্ছে।
{
    int sum=x+y;
    return sum;
}
int main()
{
    int x,y;
    scanf("%d %d", &x, &y);    // দুটো সংখ্যা ইনপুট নেওয়া হচ্ছে।
    printf("%d", sum(x,y));   // sum ফাংশনকে কল করে ইনপুটে নেওয়া দুটো সংখ্যা দিয়ে দেওয়া হচ্ছে এবং ফাংশন যা রিটার্ন করছে তা প্রিন্ট করে দেওয়া হচ্ছে।
    return 0;
}

মডিউল ১৪-৪+১৪-৫ঃ রিটার্ন + নো প্যারামিটার

এবার আমরা দেখব এমন ফাংশন যা রিটার্ন করবে কিন্তু কোন ইনপুট নিবে না অর্থাৎ কোন প্যারামিটার থাকবে না। আমরা পূর্বের উদাহরনটিই নিচ্ছি দুটি সংখ্যা যোগ করার যেন আমরা পার্থক্য খুব ভালোভাবে বুঝতে পারি।

Code:

c
#include <stdio.h>
int sum()       // sum ফাংশন ডিক্লেয়ার করা হয়েছে। যা দুটি সংখ্যার যোগফল রিটার্ন করবে তাই রিটার্ন টাইপ int। কোন প্যারামিটার নেওয়া হচ্ছে না, তাই প্যারামিটারের অংশটুকু খালি রাখা হয়েছে।
{
    int a,b;
    scanf("%d %d", &a, &b); // যেহেতু প্যারামিটার নেওয়া হচ্ছে না, তাই এই ফাংশনের ভিতরেই ইউজার থেকে ইনপুট নেওয়া হচ্ছে।
    int s=a+b;      // ইনপুট নেওয়া সংখ্যা দুটি যোগ করে স্টোর করে রাখা হচ্ছে।
    return s;       // যোগফল রিটার্ন করা হচ্ছে।
}
int main()
{
    int s=sum();    // যেহেতু ফাংশনে কোন প্যারামিটার দেওয়া যাবে না তাই মেইন ফাংশনে ইউজার থেকে ইনপুট নেওয়া হয় নি। সরাসরি ফাংশনকে কল করে দেওয়া হয়েছে কোন প্যারামিটার না দিয়ে এবং ফাংশন যা রিটার্ন করছে তা স্টোর করে রাখা হচ্ছে।
    printf("%d",s); // স্টোর করে রাখা ফাংশন থেকে রিটার্ন হয়ে আসা যোগফল প্রিন্ট করা হচ্ছে।
    return 0;
}

মডিউল ১৪-৬ + ১৪-৭ঃ নো রিটার্ন + প্যারামিটার

এবার আমরা দেখব এমন ফাংশন যা প্যারামিটার নিবে কিন্তু কোন কিছু রিটার্ন করবে না। যেহেতু সে কোন কিছু মেইন ফাংশনকে রিটার্ন করবে না তাই এখানে যোগফলটি ফাংশনের মধ্যেই প্রিন্ট করা হবে।

Code:

c
#include <stdio.h>

void sum(int x, int y)   // ফাংশন ডিক্লেয়ার করে রিটার্ন টাইপ হিসেবে void দেওয়া হয়েছে এবং প্যারামিটারে দুটি সংখ্যা নেওয়া হচ্ছে।
{
    int s=x+y;          // সংখ্যা দুটির যোগফল বের করা হচ্ছে।
    printf("%d\n", s);  // যোগফল এখানেই প্রিন্ট করা হচ্ছে যেহেতু আমরা কোন কিছু রিটার্ন করতে পারব না।
}
int main()
{
    int a,b;
    scanf("%d %d", &a, &b);    // দুটি সংখ্যা ইনপুট নেওয়া হচ্ছে।
    sum(a, b);                 // ফাংশনকে কল করে ইনপুট নেওয়া দুটি সংখ্যা প্যারামিটার হিসেবে দিয়ে দেওয়া হচ্ছে।
    return 0;
}

মডিউল ১৪-৮ + ১৪-৯ + ১৪-১০ঃ নো রিটার্ন + নো প্যারামিটার

এবার আমরা দেখব এমন ফাংশন যা প্যারামিটার ও নিবে না এবং কোন কিছু রিটার্নও করবে না। যেহেতু সে কোন কিছু প্যারামিটার হিসেবে নিবে না তাই এখানে ইনপুটও নেওয়া হবে ফাংশনের মধ্যে এবং যেহেতু সে কোন কিছু মেইন ফাংশনকে রিটার্ন করবে না তাই এখানে ফাংশনের মধ্যেই প্রিন্ট করা হবে।

Code:

c
#include <stdio.h>

void sum()       // ফাংশন ডিক্লেয়ার করা হচ্ছে। রিটার্ন টাইপ হিসেবে void দেওয়া হয়েছে যেহেতু কোন রিটার্ন নেই এবং প্যারামিটারের জায়গা ফাঁকা রাখা হয়েছে।
{
    int a,b;
    scanf("%d %d", &a, &b);   // ইনপুট নেওয়া হচ্ছে এখানে।
    int s=a+b;              // যোগফল বের করা হচ্ছে।
    printf("%d\n", s);       // যোগফল প্রিন্টও করা হচ্ছে এখানে।
}
int main()
{
    sum();    // শুধুমাত্র ফাংশনকে কল করা হচ্ছে। কোন প্যারামিটার দেওয়া হচ্ছে না।
    return 0;
}

মডিউল ১৪-১১ঃ স্কোপ্স

একটি সি প্রোগ্রামে আমরা অনেকগুলো ভেরিয়েবল অনেক জায়গায় ডিক্লেয়ার করি। কোন ভেরিয়েবলটি কোন পর্যন্ত এক্সেস করা যায় তা জানতে আমরা এখন দেখব স্কোপ্স।

আমরা যদি একটি ফাংশনে কোন ভেরিয়েবল ডিক্লেয়ার করি তাহলে মেইন ফাংশন থেকে সেই ভেরিয়েবলকে এক্সেস করা যাবে না। ভেরিয়েবলটির স্কোপ্স হচ্ছে ওই ফাংশন পর্যন্তই। ওই ফাংশনের মধ্যে যেকোন জায়গায় এক্সেস করা যাবে।

Code:

c
#include <stdio.h>
void func()
{
    int s = 100;        // একটি ভেরিয়েবল ডিক্লেয়ার করা হয়েছে। এই ভেরিয়েবল এর স্কোপ্স হচ্ছে এই ফাংশন পর্যন্ত।
}
int main()
{
    printf("%d", s);    // এই লাইনে এরর দিবে। কারন এখানে আমরা s ভেরিয়েবল কে এক্সেস করার চেষ্টা করছি যেটি এখানে ডিক্লেয়ার করা হয় নি।
}

সেইমভাবে মেইন ফাংশনে ডিক্লেয়ার করা কোন ভেরিয়েবল মেইন ফাংশনের বাইরে থেকে এক্সেস করা যাবে না।

Code:

c
#include <stdio.h>
void func()
{
    printf("%d", x);    // এই লাইনে এরর দিবে। x ভেরিয়েবলটি ডিক্লেয়ার করা হয়েছে মেইন ফাংশনে। মেইন ফাংশনের বাইরে থেকে এক্সেস করা যাবে না।
}
int main()
{
    int x = 10;
}

একটি ভেরিয়েবল এর স্কোপ্স যে পুরো ফাংশন জুড়ে ব্যাপারটি কিন্তু এমন না। মেইন ফাংশনের মধ্যে একটি লুপের মধ্যে যদি কোন ভেরিয়েবল ডিক্লেয়ার করা হয় তাহলে সেই ভেরিয়েবলটি লুপের বাইরে থেকে এক্সেস করা যাবে না।

Code:

c
#include <stdio.h>
int main()
{
    int x = 10;         // মেইন ফাংশনের মধ্যে ভেরিয়েবল ডিক্লেয়ার করা হচ্ছে x। এটি পুরো মেইন ফাংশন জুড়ে পাওয়া যাবে।
    for(int i=0; i<5; i++)   // একটি রেন্ডম লুপ চালানো হচ্ছে যেটি ৫ বার চলবে।
    {
        int y = 20;     // লুপের মধ্যে একটি ভেরিয়েবল ডিক্লেয়ার করা হচ্ছে y। এটি শুধুমাত্র লুপের মধ্যেই এক্সেস করা যাবে।
        printf("%d\n", y);   // লুপের মধ্যে y কে এক্সেস করছি তাই এরর আসবে না।
    }
    printf("%d\n", x);      // মেইন ফাংশনে ডিক্লেয়ার করা x কে এক্সেস করা হচ্ছে।
    printf("%d\n", y);      // লুপের বাইরে y কে এক্সেস করা হচ্ছে তাই এই লাইনে এরর আসবে।
}

যদি কোন ভেরিয়েবল সব ধরনের ফাংশনের বাইরে লিখা হয় তখন সেগুলোকে বলা হয় গ্লোবাল ভেরিয়েবল। আর একটি গ্লোবাল ভেরিয়েবলকে পুরো কোডের যেকোন জায়গা থেকে এক্সেস করা যায়।

Code:

c
#include <stdio.h>
int x = 10;             // গ্লোবাল ভেরিয়েবল ডিক্লেয়ার করা হয়েছে।
void func()
{
    printf("%d\n", x);  // কোন এরর আসবে না। x এর মান প্রিন্ট হবে।
}
int main()
{
    func();
    printf("%d\n", x);  // কোন এরর আসবে না। x এর মান প্রিন্ট হবে।
}

মডিউল ১৪-১২ঃ ইউজফুল বিল্ট-ইন ফাংশন

আমরা আমাদের সি প্রোগ্রামিং শেখার জার্নিতে এখন পর্যন্ত অনেকগুলো বিল্ট-ইন ফাংশন দেখেছি ( scanf(), printf(), strlen(), strcmp()... ) । এবার আমরা আরো কিছু বিল্ট-ইন ফাংশন সম্পর্কে জানব। প্রথমেই আমরা কিছু গাণিতিক ফাংশন দেখব। এই ফাংশনগুলোকে রান করতে হলে math.h এই হেডার ফাইলটি ইনক্লুড করতে হয়।

ceil(): এই ফাংশন একটি ভেলু ( double ডাটা টাইপের ) নিয়ে তার সিলিং ভেলু রিটার্ন করে। কিছু সংখ্যার সিলিং ভেলু দেখে নেই আমরা।

ceil( ৩.৯ ) = ৪

ceil( ৩.১ ) = ৪

ceil( ৩.০ ) = ৩

floor(): এই ফাংশন একটি ভেলু ( double ডাটা টাইপের ) নিয়ে তার ফ্লোর ভেলু রিটার্ন করে। ফ্লোর মূলত দশমিকের পরের অংশ বাদ দিয়ে শুধু পূর্ণ সংখ্যাটি রেখে দেয়। কিছু সংখ্যার ফ্লোর ভেলু দেখে নেই আমরা।

floor( ৩.৯ ) = ৩

floor( ৩.১ ) = ৩

floor( ৩.০ ) = ৩

round(): এই ফাংশন একটি ভেলু ( double ডাটা টাইপের ) নিয়ে তার ভেলুটি রাউন্ড করে রিটার্ন করে। দশমিকের পর ৫ বা এর অধিক থাকলে তখন তার পরের সংখ্যাটি নেওয়া হয় আর নাহলে সেই সংখ্যাটিই নেওয়া হয়। কিছু সংখ্যার রাউন্ড ভেলু দেখে নেই আমরা।

round( ৩.৯ ) = ৪

round( ৩.৪ ) = ৩

round( ৩.৫ ) = ৪

sqrt(): এই ফাংশন একটি ভেলু ( double ডাটা টাইপের ) নিয়ে তার স্কয়ার রুট ভেলুটি রিটার্ন করে। কিছু সংখ্যার স্কয়ার রুট ভেলু দেখে নেই আমরা।

sqrt( ২৫ ) = ৫

sqrt( ৩৬ ) = ৬

sqrt( ১০ ) = ৩.১৬২২৭৮

pow(): এই ফাংশন দুইটি ভেলু ( double ডাটা টাইপের ) নিয়ে প্রথমটির উপর দ্বিতীয়টি পাওয়ার (সূচক) করে রিটার্ন করে। কিছু সংখ্যার পাওয়ার দেখে নেই আমরা।

pow( ২,৩ ) = ৮

pow( ৩,২) = ৯

pow( ৩,৪ ) = ৮১

abs(): এই ফাংশন একটি ভেলু ( int ডাটা টাইপের ) নিয়ে তার এবসুলেট ভেলুটি রিটার্ন করে। কোন সংখ্যার এবসুলেট ভেলু হচ্ছে যদি সংখ্যাটি নেগেটিভ থাকে তাহলে তার সাথে -১ গুন করা হয়, আর নাহলে সংখ্যাটি যা ছিল তাই থাকে। কিছু সংখ্যার এবসুলেট ভেলু দেখে নেই আমরা। এখানে লক্ষণীয় হচ্ছে এই ফাংশনটি long long int ডাটা টাইপের জন্য কাজ করে না।

abs( ৫ ) = ৫

abs( -৫ ) = ৫

abs( -১০ ) = ১০

Code:

c
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
int main()
{
    printf("%llf\n", ceil(3.2));    // প্রিন্ট করলে ৩.২ এর সিলিং ভেলু ৪ আসবে।
    printf("%llf\n", floor(3.6));   // প্রিন্ট করলে ৩.৬ এর ফ্লোর ভেলু ৩ আসবে।
    printf("%llf\n", round(3.5));   // প্রিন্ট করলে ৩.৫ এর রাউন্ড ভেলু ৪ আসবে।
    printf("%llf\n", sqrt(25));     // প্রিন্ট করলে ২৫ এর স্কয়ার রুট ভেলু ৫ আসবে।
    printf("%llf\n", pow(4,2));     // প্রিন্ট করলে ৪^2 এর ভেলু ১৬ আসবে।
    printf("%d\n", abs(-7));        // প্রিন্ট করলে -৭ এর এবসুলেট ভেলু ৭ আসবে。
}

মডিউল ১৪-১৩ঃ Why int main and return 0

প্রোগ্রামিং শেখার সময় আমরা প্রায়ই int main() এবং return 0; দেখি। কিন্তু কেন আমরা এটি ব্যবহার করি? এটি কি শুধুই একটি রীতি, নাকি এর পেছনে বিশেষ কারণ আছে? আজকে আমরা এই বিষয়টি বিস্তারিত আলোচনা করব।

main() ফাংশন কেন int টাইপের হয়?

C বা C++ প্রোগ্রামে main() ফাংশনটি প্রোগ্রামের এন্ট্রি পয়েন্ট (Entry Point), অর্থাৎ প্রোগ্রামটি এখান থেকে শুরু হয়। main() ফাংশনের রিটার্ন টাইপ int (ইন্টিজার) হওয়ার পেছনে মূল কারণ হলো:

অপারেটিং সিস্টেম বা অন্য কোনো প্রোগ্রাম জানতে চায় যে আমাদের প্রোগ্রামটি সফলভাবে শেষ হয়েছে নাকি কোনো সমস্যা হয়েছে। return 0; দিয়ে আমরা অপারেটিং সিস্টেমকে জানাই যে প্রোগ্রামটি কোনো এরর ছাড়াই সফলভাবে শেষ হয়েছে। 0 ছাড়া অন্য কোনো মান (যেমন 1, -1 ইত্যাদি) দিয়ে এরর কোড নির্দেশ করা হয়।

return 0; কেন দরকার?

return 0; এর মূল কাজ হলো প্রোগ্রামের এক্সিট স্টেটাস নির্দেশ করা এবং প্রোগ্রামটি সফলভাবে সম্পন্ন হয়েছে তা বুঝানো।

return 1; বা অন্য কোনো নন-জিরো মান প্রোগ্রামে কোনো সমস্যা হয়েছে বুঝায়।

return 0; না দিলে কি হয়?

C99 এবং C++ স্ট্যান্ডার্ড অনুযায়ী, main() ফাংশনে return 0; না দিলেও কম্পাইলার অটোমেটিকালি return 0; যুক্ত করে নেয়। তবে, এটি স্পষ্টভাবে লেখাই ভালো প্র্যাকটিস।

উদাহরণ:

Code:

c
#include <stdio.h>

int main() {
    printf("Hello, World!\n");
    return 0; // প্রোগ্রাম সফলভাবে শেষ হয়েছে
}

Released under the MIT License.