Notes — Module 6: Methods and Interfaces¶
These are your personal study notes. Write freely and honestly. Incomplete notes are fine — they show where your understanding still needs work. Return to this file to add insights as they develop over time.
Module: [[go/6. Methods and Interfaces]] Topic: [[go]] Date started: YYYY-MM-DD Status: In progress
Concept Map¶
Sketch how the concepts in this module relate to each other. Fill in the Mermaid diagram.
mindmap
root((Methods & Interfaces))
Methods
value receiver — copies receiver
pointer receiver — mutates original
any named local type
method = function with receiver
Method Sets
T: value-receiver methods only
pointer-T: both value and pointer receivers
interface satisfaction depends on method set
addressability rule for auto-dereference
Interfaces
implicit structural satisfaction
no implements keyword
define at the consumer
keep small (1–3 methods)
Interface Values
dynamic type + dynamic value pair
nil interface vs typed nil
any / empty interface
Type Assertions and Switches
comma-ok form
type switch with cases
interface type cases in switch
Standard Interfaces
fmt.Stringer
error
io.Reader and io.Writer
sort.Interface
Design
accept interfaces return structs
small interfaces compose
avoid interface pollution
Alternative: draw this on paper, photo it, and link the image here.
Key Insights¶
The "aha moments" — the things that, once understood, made the rest clear. Be specific: "I finally understood X because Y" is more useful than "X makes sense".
- Method set asymmetry: I finally understood that
*Tgets both value- and pointer-receiver methods, butTonly gets value-receiver methods, because the compiler can always dereference a pointer but cannot always take the address of an interface's stored value (it might be a copy). - Typed nil is not nil interface: The typed-nil bug clicked when I understood that an interface is a two-word struct:
(type, value). A nil concrete pointer stored in an interface sets the type word but zeros the value word — the interface is still "not nil" because the type word is set. - Add insights as you discover them
My Understanding¶
Explain the core concepts in your own words, as if teaching them to someone else. If you can't explain it simply, you don't understand it well enough yet.
Methods and Receivers¶
Your explanation here
What I'm still unsure about: (e.g., can you define methods on a type alias? on a type from another package?)
Value vs Pointer Receivers¶
Your explanation here
What I'm still unsure about: (e.g., when exactly does the compiler auto-take the address for a method call?)
Interface Satisfaction and Method Sets¶
Your explanation here
What I'm still unsure about: (e.g., the exact rule for when T satisfies an interface vs *T)
Interface Values — The (type, value) Pair¶
Your explanation here
What I'm still unsure about: (e.g., what happens to the interface value when the concrete type goes out of scope?)
The Typed-Nil Bug¶
Your explanation here
What I'm still unsure about: (e.g., are there other situations where this pattern causes a bug beyond error returns?)
Connections to Other Topics¶
How does this module connect to things you already know?
| This module's concept | Connects to | How |
|---|---|---|
| Pointer receiver | [[go/5. Pointers]] | A pointer receiver is just a pointer parameter — same rules about mutability and indirection apply |
| Interface values as (type, value) | [[go/15. Reflection and Metaprogramming]] | reflect.TypeOf and reflect.ValueOf operate on this same (type, value) pair — interfaces are the entry point to reflection |
| error interface | [[go/8. Error Handling]] | error is just interface{ Error() string } — all of module 8 builds on this module's interface mechanics |
| sort.Interface | [[go/4. Composite Types]] | sort.Interface operates on slices — understanding slice indexing and swapping is prerequisite to implementing Len/Less/Swap |
Questions That Arose¶
Log questions as they appear. Don't stop to answer them now — just capture them. Then move the serious ones to QUESTIONS.md.
- Can you define a method on a pointer to an interface? (I think not — but why?) → added to QUESTIONS.md as Q001
- If a struct embeds a type that has methods, do those methods count toward satisfying an interface? → needs testing
- What does the compiler do with the method table (itab) at runtime? → might be answered in module 17
Code Snippets Worth Remembering¶
Patterns, idioms, or examples that captured something important.
Compile-time interface satisfaction check¶
var _ io.Writer = (*MyWriter)(nil)
// If *MyWriter doesn't implement io.Writer, this line causes a compile error.
// Use this as documentation that MyWriter is intended to satisfy io.Writer.
Why I'm saving this: This pattern gives you a named compile-time assertion. It's idiomatic in library code to document intended interface satisfaction and catch regressions early.
Pointer receiver prevents value type from satisfying interface¶
type Doer interface{ Do() }
type T struct{}
func (t *T) Do() {} // pointer receiver
var d Doer = T{} // compile error: T does not implement Doer
var d Doer = &T{} // OK: *T implements Doer
Why I'm saving this: This is the most common "does not implement" error. Solution is always to use &T{} or ensure the receiver type is consistent.
The correct nil-returning error pattern¶
func mayFail(ok bool) error {
if !ok {
return &MyError{"something failed"}
}
return nil // NOT: var err *MyError; return err
}
Why I'm saving this: The bug version (declaring a typed nil and returning it) looks correct but breaks if err != nil. Always return nil directly when there is no error.
Consumer-side interface definition¶
// In the consumer package:
type Saver interface {
Save(key, value string) error
}
// The producer package (e.g., storage) never mentions Saver.
// FileStore satisfies Saver implicitly by having the Save method.
Why I'm saving this: This is the canonical "define interfaces where you use them" pattern. It decouples packages without requiring the producer to import the consumer.
What Tripped Me Up¶
Mistakes I made, misconceptions I had, things that confused me more than they should have. Being honest here helps you later.
- Value receiver vs pointer receiver in interface context — I initially thought the compiler's auto-addressing for direct method calls also applied when storing into an interface. It doesn't. For interfaces, the method set rules are strict.
- The typed-nil bug — I initially assumed that a nil pointer of any kind returned as an error would make
err == niltrue. It doesn't. The interface wraps the pointer and carries its type.
Summary in My Own Words¶
Write a 3–5 sentence summary of this entire module without looking at any notes. If you can't do this, you need more study time.
Write your summary here after completing the module.
Last updated: YYYY-MM-DD