Question

How to Convert an int to a String in Go

gostringintegerconverters

Question

i := 123
s := string(i)

In Go, s becomes a single-character string such as '{' or another Unicode character, but I want the string value "123" instead.

How can I correctly convert an int to its decimal string representation in Go?

Short Answer

By the end of this page, you will understand why string(i) does not convert an integer like 123 into the text "123" in Go. You will learn the correct way to do this using the strconv package, when to use strconv.Itoa vs strconv.FormatInt, and how integer-to-string conversion is commonly handled in real Go code.

Concept

In Go, converting a numeric value to a string depends on what kind of conversion you want.

When you write:

s := string(i)

Go does not interpret this as “turn the number into its digits.” Instead, it treats i as a Unicode code point and creates a string containing the character represented by that code point.

For example:

fmt.Println(string(65))

outputs:

A

because 65 is the Unicode code point for A.

So if i := 123, then string(i) gives the character with code point 123, which is:

{

That is why string(i) does not produce "123".

To convert an integer to its decimal text form, use the strconv package:

strconv.Itoa(i)

This returns the string form of the number, such as "123".

Why this matters

This distinction is important in real programs because numbers and text are used differently:

  • Numbers are used for calculations.
  • Strings are used for display, logging, JSON fields, URLs, IDs, and user output.

Using the wrong conversion can lead to confusing bugs, strange characters, or invalid output.

Mental Model

Think of an int in Go as a number in a box.

There are two different ways to interpret that box:

  • As a number to display → 123 should become "123"
  • As a character code → 123 should become the character whose Unicode value is 123, which is {

So:

  • strconv.Itoa(123) means: write the number using digits
  • string(123) means: treat 123 as a character code

A simple analogy:

  • strconv.Itoa(123) is like writing the label 123 on paper.
  • string(123) is like looking up item 123 in a character table and returning the symbol found there.
Take Quiz

Syntax and Examples

The most common way to convert an int to a string in Go is with strconv.Itoa.

package main

import (
	"fmt"
	"strconv"
)

func main() {
	i := 123
	s := strconv.Itoa(i)
	fmt.Println(s)
}

Output:

123

Using strconv.FormatInt

If you are working with int64, or you want to specify the base manually, use strconv.FormatInt.

package main

import (
	"fmt"
	"strconv"
)

func main() {
	var n int64 = 123
	s := strconv.FormatInt(n, 10)
	fmt.Println(s)
}

Output:

123

The second argument, 10, means decimal format.

What string(i) actually does

package main

import "fmt"

func main() {
	i := 65
	s := string(i)
	fmt.Println(s)
}

Output:

A

This is useful only when you intentionally want a character from a Unicode code point.

Quick rule

  • Use strconv.Itoa(i) for int
  • Use strconv.FormatInt(n, 10) for int64
  • Use string(i) only when converting a code point to a character string

Step by Step Execution

Consider this example:

package main

import (
	"fmt"
	"strconv"
)

func main() {
	i := 123
	s := strconv.Itoa(i)
	fmt.Println(s)
}

Step by step:

  1. i := 123

    • A variable named i is created.
    • Its value is the integer 123.
  2. s := strconv.Itoa(i)

    • Go calls the Itoa function from the strconv package.
    • Itoa reads the integer value 123.
    • It converts that number into the string "123".
    • The result is stored in s.
  3. fmt.Println(s)

    • Go prints the contents of s.
    • Output is 123.

Now compare that with this:

package main

import "fmt"

func main() {
	i := 123
	s := string(i)
	fmt.Println(s)
}

Step by step:

  1. i := 123

    • i holds the number 123.
  2. s := string(i)

    • Go does not write the digits 1, 2, and 3.
    • It treats 123 as a Unicode code point.
    • Unicode code point 123 is {.
    • So s becomes "{".
  3. fmt.Println(s)

    • Output is {.

That is the key difference.

Real World Use Cases

Integer-to-string conversion is very common in Go programs.

Building log messages

userID := 42
msg := "processing user " + strconv.Itoa(userID)

Creating URLs or query parameters

page := 3
url := "/articles?page=" + strconv.Itoa(page)

Writing values to JSON-like text or CSV

count := 15
line := "items," + strconv.Itoa(count)

Displaying numbers in CLI tools

files := 7
fmt.Println("Processed " + strconv.Itoa(files) + " files")

Generating cache keys or map keys

id := 1001
key := "user:" + strconv.Itoa(id)

In all of these cases, the goal is to represent the number as readable text, not as a character code.

Take Quiz

Real Codebase Usage

In real Go codebases, developers usually convert integers to strings in a few common ways depending on the context.

1. Simple conversion with strconv.Itoa

For ordinary int values:

idStr := strconv.Itoa(id)

This is the most direct and readable choice.

2. Formatting inside output with fmt.Sprintf

Sometimes developers use formatted strings when building larger messages:

msg := fmt.Sprintf("user id=%d created", id)

This is helpful when multiple values are involved.

3. Validation and early returns

A converted string may be used after checking input or constraints:

func userPath(id int) string {
	if id <= 0 {
		return ""
	}
	return "/users/" + strconv.Itoa(id)
}

This pattern combines validation with a clear conversion step.

4. Configuration and environment values

Applications often need numeric values in string form when working with environment variables, command output, headers, or URLs.

port := 8080
address := ":" + strconv.Itoa(port)

5. Error messages and debugging

if retries > maxRetries {
	return fmt.Errorf("too many retries: %d", retries)
}

In practice, developers choose:

  • strconv.Itoa for direct conversion
  • fmt.Sprintf when formatting a larger string
  • string(runeValue) only when intentionally working with characters or Unicode

Common Mistakes

Mistake 1: Using string(i) for digit conversion

Broken code:

i := 123
s := string(i)
fmt.Println(s)

This does not print 123. It prints the character for Unicode code point 123.

Correct code:

i := 123
s := strconv.Itoa(i)
fmt.Println(s)

Mistake 2: Forgetting to import strconv

Broken code:

package main

import "fmt"

func main() {
	i := 123
	s := strconv.Itoa(i)
	fmt.Println(s)
}

This fails because strconv was not imported.

Correct code:

import (
	"fmt"
	"strconv"
)

Mistake 3: Mixing int and int64 carelessly

Broken code:

var n int64 = 123
s := strconv.Itoa(n)

strconv.Itoa expects an int, not int64.

Correct options:

s := strconv.FormatInt(n, 10)

or, if safe and appropriate:

s := strconv.Itoa(int(n))

Mistake 4: Using fmt.Sprintf when only conversion is needed

This is valid:

s := fmt.Sprintf("%d", i)

But for simple int to string conversion, this is usually clearer:

s := strconv.Itoa(i)

Mistake 5: Confusing bytes, runes, and strings

A number can represent different things in Go:

  • a numeric value
  • a byte
  • a rune (Unicode code point)

So this:

string(49)

returns:

"1"

because 49 is the code point for the character 1, not because Go converted the number 49 into its decimal text automatically.

Comparisons

ApproachUse caseExampleResult for 123
strconv.Itoa(i)Convert int to decimal stringstrconv.Itoa(123)"123"
strconv.FormatInt(n, 10)Convert int64 to decimal stringstrconv.FormatInt(123, 10)"123"
fmt.Sprintf("%d", i)Format values into a larger stringfmt.Sprintf("%d", 123)"123"
string(i)Convert Unicode code point to stringstring(123)"{"

strconv.Itoa vs fmt.Sprintf

Featurestrconv.Itoafmt.Sprintf
PurposeSimple int-to-string conversionGeneral string formatting
Best forDirect conversionBuilding formatted messages
ReadabilityVery clear for this taskBetter when formatting multiple values
PerformanceTypically more directMore flexible, but heavier

Rule of thumb

  • Need only the digits of an int? Use strconv.Itoa.
  • Need to format a sentence or multiple values? Use fmt.Sprintf.
  • Need a character from a code point? Use string(i).
Take Quiz

Cheat Sheet

import "strconv"

Convert int to string

s := strconv.Itoa(i)

Convert int64 to string

s := strconv.FormatInt(n, 10)

Convert uint64 to string

s := strconv.FormatUint(n, 10)

Format with fmt

s := fmt.Sprintf("%d", i)

Important rule

string(123)

means:

  • convert Unicode code point 123 to a string
  • result: "{"

It does not mean decimal conversion.

Common choices

  • strconv.Itoa(i) → best for int
  • strconv.FormatInt(n, 10) → best for int64
  • fmt.Sprintf("%d", i) → useful for formatted output
  • string(i) → only for rune/code point conversion

FAQ

Why does string(123) not return "123" in Go?

Because string(123) treats 123 as a Unicode code point and converts it to the corresponding character, which is {.

What is the correct way to convert an int to a string in Go?

Use:

strconv.Itoa(i)

When should I use strconv.FormatInt instead of strconv.Itoa?

Use strconv.FormatInt when your value is int64 or when you want to choose a base such as binary, decimal, or hexadecimal.

Is fmt.Sprintf("%d", i) also valid?

Yes. It works well, especially when building larger formatted strings. For simple conversion, strconv.Itoa is usually clearer.

What does string(65) return in Go?

It returns "A" because 65 is the Unicode code point for A.

Can I convert negative integers with strconv.Itoa?

Yes.

strconv.Itoa(-42) // "-42"

Does Go automatically convert numbers to strings?

No. Go is explicit about type conversion, so you usually need strconv or fmt for numeric text output.

Take Quiz

Mini Project

Description

Build a small Go program that creates user profile URLs from numeric user IDs. This demonstrates the practical need to convert integers into strings when building text values such as paths, keys, and messages.

Goal

Create a program that converts integer user IDs into strings and uses them to build readable profile URLs.

Requirements

  • Read or define at least three integer user IDs.
  • Convert each int ID to a string correctly.
  • Build a URL in the form /users/<id> for each ID.
  • Print each generated URL.
  • Do not use string(id) for the conversion.
Take Quiz

Keep learning

Related questions

View more