C String strtok() Function

Beginner
⏱️ 11 min read
📚 Updated: Jul 2026
🎯 5 Examples
<string.h>

What You’ll Learn

The strtok() function breaks a C string into tokens using delimiter characters such as spaces, commas, or tabs. It is a classic tool for parsing command-line arguments, CSV fields, and log lines—once you understand that it modifies the original buffer.

01

Split

Tokens.

02

First call

Pass str.

03

Later

Pass NULL.

04

In place

Writes \0.

05

Delims

Char set.

06

Not thread

Static state.

Definition and Usage

strtok scans a modifiable string and returns pointers to consecutive tokens. Delimiter characters are replaced with '\0', so each token becomes its own null-terminated substring inside the same array.

The first call uses the string pointer. Every following call passes NULL so strtok continues where it left off. When no tokens remain, it returns NULL.

💡
Beginner Tip

Declare char sentence[] = "word1 word2"; (array), not char *p = "word1 word2"; (read-only literal). strtok must write into the buffer—literals cannot be modified safely.

📝 Syntax

Standard C declaration:

C
char *strtok(char *str, const char *delimiters);

Parameters

  • str — on the first call, the modifiable string to tokenize; on later calls, NULL.
  • delimiters — C-string listing characters that separate tokens (space, comma, tab, etc.).

Return Value

  • Pointer to the next token (null-terminated substring inside the original buffer).
  • NULL when no more tokens are found.

Header

  • #include <string.h>

⚡ Quick Reference

Input bufferdelimitersTokens (in order)
"This is a sample sentence."" "This, is, a, sample, sentence.
"one,two;three"",;"one, two, three
"a b" (two spaces)" "a, b (empty skipped)
"done"" "done (single token)
First token
strtok(buf, " ,")

Initial call

Next token
strtok(NULL, " ,")

Continue

Loop
while (t = strtok(...))

All tokens

Safe copy
strcpy(copy, src)

Preserve src

Examples Gallery

Compile with gcc strtok.c -std=c11 -o strtok. Use a char[] buffer for every example that calls strtok directly.

📚 Getting Started

Tokenize a sentence on spaces, matching the reference tutorial.

Example 1 — Split a Sentence into Words

Break "This is a sample sentence." on space delimiters.

C
#include <stdio.h>
#include <string.h>

int main(void) {
    char sentence[] = "This is a sample sentence.";
    const char *delimiters = " ";

    char *token = strtok(sentence, delimiters);

    while (token != NULL) {
        printf("Token: %s\n", token);
        token = strtok(NULL, delimiters);
    }

    return 0;
}

How It Works

The first strtok(sentence, ...) returns "This". Each strtok(NULL, ...) picks up the next word. Delimiter spaces are overwritten with '\0' inside sentence.

Example 2 — Multiple Delimiter Characters

Split on commas, semicolons, or spaces in one delimiter set.

C
#include <stdio.h>
#include <string.h>

int main(void) {
    char line[] = "apple, banana; cherry  date";

    char *token = strtok(line, " ,;");

    while (token != NULL) {
        printf("[%s]\n", token);
        token = strtok(NULL, " ,;");
    }

    return 0;
}

How It Works

Any character listed in " ,;" acts as a separator. Consecutive delimiters are skipped, so you do not get empty tokens between fields.

📈 Practical Patterns

Preserve originals, parse CSV-style data, and compare with span functions.

Example 3 — Copy Before Tokenizing

Keep the source string intact by tokenizing a duplicate buffer.

C
#include <stdio.h>
#include <string.h>

int main(void) {
    const char *original = "red|green|blue";
    char buffer[64];

    strcpy(buffer, original);

    char *color = strtok(buffer, "|");

    printf("Original still: %s\n", original);

    while (color != NULL) {
        printf("Color: %s\n", color);
        color = strtok(NULL, "|");
    }

    return 0;
}

How It Works

strcpy copies into modifiable buffer. strtok destroys delimiter bytes only in the copy, leaving original unchanged.

Example 4 — Parse Simple CSV Fields

Read name, age, and city from a comma-separated line.

C
#include <stdio.h>
#include <string.h>

int main(void) {
    char record[] = "Mari,28,Chennai";
    char *field;
    int column = 0;

    field = strtok(record, ",");

    while (field != NULL) {
        printf("Column %d: %s\n", column++, field);
        field = strtok(NULL, ",");
    }

    return 0;
}

How It Works

Each comma becomes '\0'. This pattern works for simple CSV without quoted commas. Real CSV parsers need more rules.

Example 5 — strtok() vs strspn()/strcspn()

See how strtok mutates memory while span functions only measure.

C
#include <stdio.h>
#include <string.h>

int main(void) {
    char data[] = "  alpha  beta";
    const char *cursor = data;

    size_t skip = strspn(cursor, " \t");
    size_t len  = strcspn(cursor + skip, " \t");

    printf("Span token: %.*s\n", (int)len, cursor + skip);
    printf("Buffer unchanged mid-parse: [%s]\n", data);

    char *tok = strtok(data, " \t");
    printf("strtok first: %s\n", tok);
    printf("Buffer after strtok: [%s]\n", data);

    return 0;
}

How It Works

strspn/strcspn are read-only and return lengths. strtok writes nulls over delimiters—choose spans when you must preserve the original text.

🚀 Common Use Cases

  • Word splitting — break sentences or commands into individual tokens.
  • CSV and config lines — parse key=value or comma-separated records.
  • Path components — split on '/' or '\\' (simple cases).
  • Log parsing — extract timestamp, level, and message fields.
  • Teaching parsers — introduce tokenization before building full lexer logic.

🧠 How strtok() Works

1

Skip delimiters

Advance past any leading delimiter characters.

Start
2

Mark token start

Remember where the current token begins.

Token
3

Write \0 at delim

Replace the next delimiter with null and save position for NULL call.

Split
=

char* token

Pointer to token, or NULL when finished.

📝 Notes

  • Modifies the input buffer by inserting '\0' at delimiter positions.
  • Requires a modifiable char[] buffer—not a string literal pointer.
  • Uses internal static state; not safe across threads or nested tokenization of two strings.
  • POSIX provides strtok_r() with an explicit context pointer for reentrancy.
  • Consecutive delimiters produce no empty tokens; they are treated as one separator run.

⚡ Optimization

strtok is efficient for one-pass splitting of moderate strings. For complex parsing (quoted fields, nested delimiters), a dedicated parser or manual cursor with strspn/strcspn scales better. Copy the source once if you need both tokens and the original layout.

Conclusion

strtok() is the standard C way to split strings on delimiter characters. Pass the buffer on the first call, NULL afterward, and always remember that it destroys delimiters in place.

For multithreaded code, prefer strtok_r() or non-destructive span-based parsing.

💡 Best Practices

✅ Do

  • Use char buffer[] or copy with strcpy
  • Pass NULL on subsequent calls
  • Loop until token == NULL
  • Use strtok_r in threaded programs (POSIX)
  • Include <string.h>

❌ Don’t

  • Tokenize string literals directly
  • Assume the original string stays unchanged
  • Run two strtok loops on different strings at once
  • Use in multithreaded code without strtok_r
  • Parse real CSV with embedded commas using only strtok

Key Takeaways

Knowledge Unlocked

Five things to remember about strtok()

Use these points when splitting strings in C.

5
Core concepts
📝 02

NULL next

Continue.

Pattern
⚠️ 03

Mutates

Writes \0.

Safety
📈 04

Skip empty

Runs.

Behavior
💬 05

Not thread

strtok_r.

Compare

❓ Frequently Asked Questions

strtok() splits a string into tokens separated by delimiter characters. Each call returns a pointer to the next token, or NULL when no tokens remain.
char* strtok(char* str, const char* delimiters); Include <string.h>. On the first call pass the string to split. On later calls pass NULL to continue tokenizing the same string.
Yes. strtok() writes null characters (\0) over delimiter bytes inside the buffer. Use a modifiable char array, not a string literal, unless you copy the text first.
strtok() keeps internal state about where it stopped. NULL tells it to continue from the previous position in the same string.
No. Standard strtok() uses static internal state. In multithreaded programs use strtok_r() (POSIX) or tokenize with strspn/strcspn instead.
strtok() treats a run of delimiter characters as one separator and skips empty tokens between them.
Did you know?

Because strtok keeps hidden state between calls, calling it from two places (or on two strings alternately) corrupts parsing. The reentrant variant strtok_r(char *str, const char *delim, char **saveptr) stores progress in saveptr you control—making it safe for threads and nested splits when available.

Continue the String Functions Series

Split strings with strtok(), then explore case conversion with strupr().

Next: strupr() →

About the author

Mari Selvan M P
Mari Selvan M P 🔗

Developer, cloud engineer, and technical writer

  • Experience 12 years building web and cloud systems
  • Focus Full Stack Development, AWS, and Developer Education

I write practical tutorials so students and working developers can learn by doing—from databases and APIs to deployment on AWS.

6 people found this page helpful