Greedy Longest-Match Tokenization of a String Against a Fixed Vocabulary

Quick Overview

Tokenize a string against a fixed vocabulary by repeatedly taking the longest vocabulary entry that matches at the current position, and return the token IDs in order. It tests exact greedy semantics, efficient prefix matching over up to 100,000 characters, and careful handling of overlapping vocabulary entries.

Greedy Longest-Match Tokenization of a String Against a Fixed Vocabulary

Company: Anthropic

Role: Software Engineer

Category: Coding & Algorithms

Difficulty: medium

Interview Round: Onsite

A tokenizer splits text into tokens drawn from a fixed vocabulary. You are given a string `text` and a list `vocab` of distinct, non-empty strings. The token ID of `vocab[i]` is `i`. Tokenize `text` with the **greedy longest-match** rule: start at the beginning of `text`; at the current position, choose the longest vocabulary string that `text` continues with at that position, emit its token ID, and move the position forward by that string's length. Repeat until the whole of `text` has been consumed. Return the list of emitted token IDs, in order. ### Function Signature ```python def longest_match_tokenize(text: str, vocab: list[str]) -> list[int]: ``` ### Rules - The choice at each position is always the longest matching vocabulary string, even when a different choice would produce fewer tokens overall. - Because vocabulary strings are distinct, the longest match at a position is unique, so the output is uniquely determined. - Matching is exact and case-sensitive; spaces and punctuation are ordinary characters. ### Constraints - `1 <= len(text) <= 100000` - `1 <= len(vocab) <= 10000` - `1 <= len(vocab[i]) <= 50` for every `i`, and the total length of all vocabulary strings is at most `200000`. - All vocabulary strings are distinct. - `text` and every vocabulary string consist of printable ASCII characters (character codes 32 to 126 inclusive). - Every character that occurs in `text` is also present in `vocab` as a single-character string, so tokenization never gets stuck. - The output has between `1` and `len(text)` token IDs, each in the range `0` to `len(vocab) - 1`. ### Examples **Example 1** - Input: `text = "abcab"`, `vocab = ["a", "b", "c", "ab", "abc"]` - Output: `[4, 3]` - Explanation: At position 0 the candidates are `"a"`, `"ab"` and `"abc"`; the longest is `"abc"` (ID 4). At position 3 the candidates are `"a"` and `"ab"`; the longest is `"ab"` (ID 3). **Example 2** - Input: `text = "abcd"`, `vocab = ["a", "b", "c", "d", "ab", "bcd"]` - Output: `[4, 2, 3]` - Explanation: At position 0 the longest match is `"ab"`, leaving `"cd"`, which is tokenized as `"c"` then `"d"`. The split `"a"` + `"bcd"` would use only two tokens, but greedy longest-match never looks ahead. **Example 3** - Input: `text = "to be"`, `vocab = [" ", "b", "e", "o", "t", "to", "be", " b"]` - Output: `[5, 7, 2]` - Explanation: `"to"` (ID 5) is the longest match at position 0, `" b"` (ID 7) beats `" "` at position 2, and `"e"` (ID 2) remains.

Overview: Tokenize a string against a fixed vocabulary by repeatedly taking the longest vocabulary entry that matches at the current position, and return the token IDs in order. It tests exact greedy semantics, efficient prefix matching over up to 100,000 characters, and careful handling of overlapping vocabulary entries.

|Home/Coding & Algorithms/Anthropic
Anthropic logo
Anthropic
Sep 18, 2026
mediumSoftware EngineerOnsiteCoding & Algorithms
0
0

A tokenizer splits text into tokens drawn from a fixed vocabulary. You are given a string text and a list vocab of distinct, non-empty strings. The token ID of vocab[i] is i.

Tokenize text with the greedy longest-match rule: start at the beginning of text; at the current position, choose the longest vocabulary string that text continues with at that position, emit its token ID, and move the position forward by that string's length. Repeat until the whole of text has been consumed.

Return the list of emitted token IDs, in order.

Function Signature

def longest_match_tokenize(text: str, vocab: list[str]) -> list[int]:

Rules

  • The choice at each position is always the longest matching vocabulary string, even when a different choice would produce fewer tokens overall.
  • Because vocabulary strings are distinct, the longest match at a position is unique, so the output is uniquely determined.
  • Matching is exact and case-sensitive; spaces and punctuation are ordinary characters.

Constraints

  • 1 <= len(text) <= 100000
  • 1 <= len(vocab) <= 10000
  • 1 <= len(vocab[i]) <= 50 for every i , and the total length of all vocabulary strings is at most 200000 .
  • All vocabulary strings are distinct.
  • text and every vocabulary string consist of printable ASCII characters (character codes 32 to 126 inclusive).
  • Every character that occurs in text is also present in vocab as a single-character string, so tokenization never gets stuck.
  • The output has between 1 and len(text) token IDs, each in the range 0 to len(vocab) - 1 .

Examples

Example 1

  • Input: text = "abcab" , vocab = ["a", "b", "c", "ab", "abc"]
  • Output: [4, 3]
  • Explanation: At position 0 the candidates are "a" , "ab" and "abc" ; the longest is "abc" (ID 4). At position 3 the candidates are "a" and "ab" ; the longest is "ab" (ID 3).

Example 2

  • Input: text = "abcd" , vocab = ["a", "b", "c", "d", "ab", "bcd"]
  • Output: [4, 2, 3]
  • Explanation: At position 0 the longest match is "ab" , leaving "cd" , which is tokenized as "c" then "d" . The split "a" + "bcd" would use only two tokens, but greedy longest-match never looks ahead.

Example 3

  • Input: text = "to be" , vocab = [" ", "b", "e", "o", "t", "to", "be", " b"]
  • Output: [5, 7, 2]
  • Explanation: "to" (ID 5) is the longest match at position 0, " b" (ID 7) beats " " at position 2, and "e" (ID 2) remains.

Submit Your Answer to Earn 20XP

Sign in to leave a comment

Loading comments...