Unit 2 · Lesson 318 minAcademic review pending

Your first function of your own

A function with no arguments still needs a prototype, a definition, and a call — and understanding those three parts explains most function errors.

Choose explanation

After this lesson

You should be able to

  • Write a void function that takes no arguments.
  • Explain what a prototype tells the compiler and why it comes first.
  • Trace control as it moves from main into a function and back.
01

Three parts, in this order

A function you write has a prototype near the top, a definition further down, and one or more calls inside main. The prototype is a promise: a function with this name, these parameters, and this return type exists somewhere. It exists so the compiler can check your calls before it has read the definition.

void appears twice and means two different things. The first void is the return type: this function hands nothing back. The void in the parentheses is the parameter list: this function takes nothing in.

Prototype, call, definition
#include <stdio.h>

void print_banner(void);   /* prototype: promise */

int main(void)
{
    print_banner();        /* call */
    printf("Marks report\n");
    print_banner();        /* call it again */
    return 0;
}

void print_banner(void)    /* definition: the actual work */
{
    printf("========================\n");
}
02

Where control goes

When main reaches print_banner(), execution jumps into that function, runs its body, and returns to the line right after the call. main is paused, not finished — its variables are untouched and waiting.

A void function ends when it reaches its closing brace; you do not need a return statement. You may write a bare return; to leave early, but return with a value is an error in a void function.

03

Why bother, if it takes nothing?

Because the banner is now defined in one place. Change it from equals signs to dashes and every use changes together. Without the function you would edit each printf and miss one — that missed one is the actual bug this prevents.

It also names the intent. print_banner() says what is happening; a row of equals signs inside a printf does not.

Try it yourself

Write a program with two functions of your own — one that prints a menu and one that prints a separator line — and call them from main.

Need a hint?

Both take nothing and return nothing. Both need a prototype above main.

Check the worked solution

print_line is called from both main and print_menu, which is exactly the reuse a structure chart would show as one box with two parents. Because the separator exists once, changing its width is a one-line edit that updates every appearance.

#include <stdio.h>

void print_line(void);
void print_menu(void);

int main(void)
{
    print_menu();
    printf("Your choice: ");
    return 0;
}

void print_line(void)
{
    printf("------------------------\n");
}

void print_menu(void)
{
    print_line();
    printf("1. Add marks\n");
    printf("2. View report\n");
    printf("3. Exit\n");
    print_line();
}

Quick check

What does the prototype void greet(void); tell the compiler?

Select an answer to check your thinking.

Why this lesson exists

Syllabus mapping

Functions without Arguments · Top-Down Design and Structure Charts

Maps to course outcome CO4.