← Back to Go Course | Chapter 6: Structs & Methods | Lesson 5 of 6

Constructor Patterns

Go doesn't have a built-in constructor keyword, so programmers write a plain function named New___ whose only job is to build and hand back a ready-to-use struct.
Syntax
go
func NewName(param type) *Name {
    return &Name{Field: param}
}

A Basic Constructor Function

Since Go has no constructor keyword, the idiomatic pattern is a plain function, usually named NewType, that builds a struct value (often with some setup logic) and returns it.

Note: Naming the function NewX for a type X is the near-universal Go convention.

Example: A Basic Constructor Function

markup
// Every Go file belongs to a package; main builds an executable
package main

// Import the fmt package
import "fmt"

// Define a struct type named Person
type Person struct {
	Name string
	Age  int
}

// Define the function NewPerson
func NewPerson(name string, age int) Person {
	// Send Person{Name: name, Age: age} back to the caller
	return Person{Name: name, Age: age}
}

// main is where the program starts running
func main() {
	// Short declaration: create p and infer the type
	p := NewPerson("Divya", 27)
	// Print the values followed by a newline
	fmt.Println(p)
}

Validating Input in a Constructor

A constructor function is a natural place to validate arguments and return an error if they're invalid, keeping bad data from ever forming a struct in the first place.

Example: Validating Input in a Constructor

markup
// Every Go file belongs to a package; main builds an executable
package main

// Import the packages this program uses
import (
	"errors"
	"fmt"
)

// Define a struct type named Account
type Account struct {
	Balance float64
}

// Define the function NewAccount
func NewAccount(initial float64) (*Account, error) {
	// Check whether initial < 0
	if initial < 0 {
		return nil, errors.New("initial balance cannot be negative")
	}
	return &Account{Balance: initial}, nil
}

// main is where the program starts running
func main() {
	// Short declaration: create acc, err and infer the type
	acc, err := NewAccount(100)
	// Print the values followed by a newline
	fmt.Println(acc, err)
}

Returning a Pointer from a Constructor

When a type has pointer-receiver methods, it's common for its constructor to return a *Type directly, so the value is immediately ready to be mutated through those methods without extra addressing.

Example: Returning a Pointer from a Constructor

markup
// Every Go file belongs to a package; main builds an executable
package main

// Import the fmt package
import "fmt"

// Define a struct type named Counter
type Counter struct {
	value int
}

// Define the function NewCounter
func NewCounter() *Counter {
	// Send &Counter{value: 0} back to the caller
	return &Counter{value: 0}
}

// Define the method Increment on type Counter
func (c *Counter) Increment() {
	c.value++
}

// main is where the program starts running
func main() {
	// Short declaration: create c and infer the type
	c := NewCounter()
	c.Increment()
	c.Increment()
	fmt.Println(c.value)
}
Related Topics
{# common_mistakes/chapter_summary/browser_support: on Hindi pages the view already swaps in the hi_ translation fields (or blanks these out if untranslated), so this renders correctly for both languages without a lang_code check here. #}
Common Mistakes
  1. Expecting a special constructor syntax like other languages -- Go just uses ordinary functions, conventionally named NewXxx.
  2. Exporting all struct fields when a constructor is meant to enforce invariants, allowing callers to bypass validation by setting fields directly.
  3. Returning a struct value from a NewXxx function when a pointer was intended, causing inconsistency with the type's other pointer-receiver methods.
Chapter Summary
  • Go has no dedicated constructor syntax -- a plain function conventionally named NewType builds and returns a value.
  • Constructor functions can validate inputs and set sensible defaults before returning the struct.
  • Returning a pointer (*Type) from a constructor is common when the type has pointer-receiver methods.
  • Unexported fields combined with a constructor function enforce that objects are only created through valid initial states.
🔒

Chapter Quiz — Complete all 6 topics to unlock

0/6 topics done

Complete these topics first:

Login to run this code

C/C++/Java/PHP execution requires a free account. Your code is saved — you'll land right back in the editor after logging in.