{"id":1092,"date":"2026-08-17T00:45:11","date_gmt":"2026-08-17T00:45:11","guid":{"rendered":"https:\/\/www.devopsschool.com\/tutorials\/?p=1092"},"modified":"2026-08-17T00:45:12","modified_gmt":"2026-08-17T00:45:12","slug":"go-tutorials-generics","status":"publish","type":"post","link":"https:\/\/www.devopsschool.com\/tutorials\/go-tutorials-generics\/","title":{"rendered":"Go Tutorials: Generics"},"content":{"rendered":"\n<h2 class=\"wp-block-heading\">1. What are Generics?<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\"><strong>Generics let you write one piece of code that works with multiple types while keeping Go&#8217;s compile-time type safety.<\/strong><\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Suppose you want a function that checks whether a slice contains a value.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Without generics, you might write:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>ContainsInt(...)\nContainsString(...)\nContainsFloat(...)\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">With generics, you can write:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Contains(...)\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">once and use it with different types.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">The main idea is:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\">\n<p class=\"wp-block-paragraph\"><strong>Write the algorithm once. Let the type vary.<\/strong><\/p>\n<\/blockquote>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">2. Why do we need Generics?<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Imagine these two functions:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func ContainsInt(items &#91;]int, target int) bool {\n    \/\/ ...\n}\n\nfunc ContainsString(items &#91;]string, target string) bool {\n    \/\/ ...\n}\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The logic is identical.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Only the type changes.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Generics remove this duplication.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Instead, we can say:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Contains&#91;T comparable](items &#91;]T, target T) bool\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Here <code>T<\/code> means:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\">\n<p class=\"wp-block-paragraph\">&#8220;There will be a type here, but I don&#8217;t need to know exactly which type while writing this function.&#8221;<\/p>\n<\/blockquote>\n\n\n\n<p class=\"wp-block-paragraph\"><code>T<\/code> might later become:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>int\nstring\nfloat64\nbool\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">depending on how the function is called.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">3. Complete Copy-Paste Example<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Save this as:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>main.go\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Then run:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>go run main.go\n<\/code><\/pre>\n\n\n\n<pre class=\"wp-block-code\"><code>package main\n\nimport \"fmt\"\n\n\/\/ Contains is a generic function.\n\/\/\n\/\/ T is a TYPE PARAMETER.\n\/\/\n\/\/ \"comparable\" means T must support:\n\/\/     ==\n\/\/     !=\n\/\/\n\/\/ Examples of comparable types:\n\/\/     int\n\/\/     string\n\/\/     float64\n\/\/     bool\n\/\/\n\/\/ items &#91;]T means:\n\/\/     a slice containing values of type T\n\/\/\n\/\/ target T means:\n\/\/     the value we are searching for must also be type T\n\/\/\n\/\/ bool means:\n\/\/     the function returns true or false\nfunc Contains&#91;T comparable](items &#91;]T, target T) bool {\n\n\t\/\/ item automatically has type T.\n\tfor _, item := range items {\n\n\t\t\/\/ This works because T is \"comparable\".\n\t\tif item == target {\n\t\t\treturn true\n\t\t}\n\t}\n\n\treturn false\n}\n\nfunc main() {\n\n\t\/\/ -------------------------\n\t\/\/ Example 1: int\n\t\/\/ -------------------------\n\n\tnumbers := &#91;]int{10, 20, 30, 40}\n\n\tfmt.Println(Contains(numbers, 20))\n\t\/\/ Output: true\n\n\tfmt.Println(Contains(numbers, 99))\n\t\/\/ Output: false\n\n\n\t\/\/ -------------------------\n\t\/\/ Example 2: string\n\t\/\/ -------------------------\n\n\tnames := &#91;]string{\"Alice\", \"Bob\", \"Charlie\"}\n\n\tfmt.Println(Contains(names, \"Bob\"))\n\t\/\/ Output: true\n\n\tfmt.Println(Contains(names, \"David\"))\n\t\/\/ Output: false\n}\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Output<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>true\nfalse\ntrue\nfalse\n<\/code><\/pre>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">4. How does it work?<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">The most important line is:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Contains&#91;T comparable](items &#91;]T, target T) bool\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Break it into pieces.<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Part<\/th><th>Meaning<\/th><\/tr><\/thead><tbody><tr><td><code>func<\/code><\/td><td>Create a function<\/td><\/tr><tr><td><code>Contains<\/code><\/td><td>Function name<\/td><\/tr><tr><td><code>[T comparable]<\/code><\/td><td>Declare generic type <code>T<\/code><\/td><\/tr><tr><td><code>T<\/code><\/td><td>Placeholder for a real type<\/td><\/tr><tr><td><code>comparable<\/code><\/td><td>Restricts T to types supporting <code>==<\/code> and <code>!=<\/code><\/td><\/tr><tr><td><code>items []T<\/code><\/td><td>Slice containing T values<\/td><\/tr><tr><td><code>target T<\/code><\/td><td>Value of the same type T<\/td><\/tr><tr><td><code>bool<\/code><\/td><td>Function returns true or false<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">The generic-specific part is:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;T comparable]\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">You can mentally read it as:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\">\n<p class=\"wp-block-paragraph\">&#8220;This function works with some type called <code>T<\/code>, as long as values of T can be compared.&#8221;<\/p>\n<\/blockquote>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">5. What is <code>T<\/code>?<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\"><code>T<\/code> is simply a <strong>type parameter<\/strong>.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">It is a placeholder for a real type.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">For example:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Contains(numbers, 20)\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\"><code>numbers<\/code> is:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;]int\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">So Go understands:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>T = int\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Therefore, conceptually, the function behaves like:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Contains(items &#91;]int, target int) bool\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">But then we call:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Contains(names, \"Bob\")\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\"><code>names<\/code> is:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;]string\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">So now Go understands:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>T = string\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Conceptually:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Contains(items &#91;]string, target string) bool\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">You wrote <strong>one function<\/strong>, but Go can safely use it with different types.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">6. Type inference<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Notice that we wrote:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Contains(numbers, 20)\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">We did <strong>not<\/strong> write:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Contains&#91;int](numbers, 20)\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Both forms are possible:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Contains&#91;int](numbers, 20)\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">But normally you don&#8217;t need to specify <code>int<\/code>.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Go looks at:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>numbers\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">and sees:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;]int\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">so it automatically determines:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>T = int\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">This is called <strong>type inference<\/strong>.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">7. What is <code>comparable<\/code>?<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Look again:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;T comparable]\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\"><code>comparable<\/code> is a built-in Go constraint.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">It means:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\">\n<p class=\"wp-block-paragraph\">T must be a type that can be compared using <code>==<\/code> and <code>!=<\/code>.<\/p>\n<\/blockquote>\n\n\n\n<p class=\"wp-block-paragraph\">For example:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>10 == 20\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">valid.<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>\"Alice\" == \"Bob\"\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">valid.<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>true == false\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">valid.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Therefore these types work well with our function:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>int\nstring\nbool\nfloat64\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Our function contains:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>if item == target\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">So Go needs to know that <code>T<\/code> supports <code>==<\/code>.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">That is why we use:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>comparable\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">instead of:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>any\n<\/code><\/pre>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">8. What is <code>any<\/code>?<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Another very common generic constraint is:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>any\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Example syntax:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Something&#91;T any](value T)\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\"><code>any<\/code> means:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\">\n<p class=\"wp-block-paragraph\">T can be any type.<\/p>\n<\/blockquote>\n\n\n\n<p class=\"wp-block-paragraph\">The difference is:<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Constraint<\/th><th>Meaning<\/th><\/tr><\/thead><tbody><tr><td><code>T any<\/code><\/td><td>T can be practically any Go type<\/td><\/tr><tr><td><code>T comparable<\/code><\/td><td>T must support <code>==<\/code> and <code>!=<\/code><\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">Our function needs:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>item == target\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Therefore:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>comparable\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">is the correct choice.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">9. Visual Model<\/h1>\n\n\n\n<pre class=\"wp-block-code\"><code>flowchart LR\n    A&#91;\"Contains(numbers, 20)\"] --&gt; B&#91;\"Go sees &#91;]int\"]\n    B --&gt; C&#91;\"T = int\"]\n\n    D&#91;\"Contains(names, 'Bob')\"] --&gt; E&#91;\"Go sees &#91;]string\"]\n    E --&gt; F&#91;\"T = string\"]\n\n    C --&gt; G&#91;\"Same Contains function\"]\n    F --&gt; G\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Think of <code>T<\/code> as an empty type slot.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">First call:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>T \u2192 int\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Second call:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>T \u2192 string\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Same algorithm.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Different types.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">10. Why not just use <code>any<\/code> everywhere?<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Before generics, code sometimes accepted values using:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>interface{}\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Modern Go has the equivalent alias:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>any\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">You could write something like:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Something(value any)\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">but now the function does not preserve much information about the actual type.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Generics are different.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Consider:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Contains&#91;T comparable](items &#91;]T, target T)\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The compiler knows that:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>items contains T\ntarget is T\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The two values must therefore agree on their type.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">That relationship is one of the major benefits of generics.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">11. Normal Functions vs <code>any<\/code> vs Generics<\/h1>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Feature<\/th><th>Concrete Function<\/th><th><code>any<\/code> \/ <code>interface{}<\/code><\/th><th>Generics<\/th><\/tr><\/thead><tbody><tr><td>Works with multiple types<\/td><td>\u274c<\/td><td>\u2705<\/td><td>\u2705<\/td><\/tr><tr><td>Preserves type relationships<\/td><td>\u2705<\/td><td>\u274c<\/td><td>\u2705<\/td><\/tr><tr><td>Compile-time type checking<\/td><td>\u2705<\/td><td>Limited for operations on underlying values<\/td><td>\u2705<\/td><\/tr><tr><td>Often requires type assertions<\/td><td>\u274c<\/td><td>\u2705<\/td><td>\u274c<\/td><\/tr><tr><td>Avoids duplicate algorithms<\/td><td>\u274c<\/td><td>\u2705<\/td><td>\u2705<\/td><\/tr><tr><td>Good choice for reusable algorithms<\/td><td>Sometimes<\/td><td>Sometimes<\/td><td>\u2705<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">For example, if an algorithm should work identically for:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;]int\n&#91;]string\n&#91;]float64\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">generics are often a natural solution.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">12. When should you use Generics?<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Use generics when the <strong>same algorithm<\/strong> needs to work with several types.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Good examples include:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Contains\nMin\nMax\nFilter\nMap\nStack\nQueue\nSet\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">For example:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Contains int\nContains string\nContains float64\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">is a strong signal that generics may help.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Instead of:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>ContainsInt()\nContainsString()\nContainsFloat()\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">you can have:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Contains()\n<\/code><\/pre>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">13. When should you NOT use Generics?<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Don&#8217;t use generics simply because they exist.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">If your function only works with strings:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func NormalizeUsername(name string) string\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">there is usually no reason to change it to:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func NormalizeUsername&#91;T ...]\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Keep the concrete version.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">A useful rule is:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\">\n<p class=\"wp-block-paragraph\"><strong>Use generics when the algorithm is the same but the data type changes.<\/strong><\/p>\n<\/blockquote>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">14. Where are Generics commonly used?<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">You will commonly encounter generics in:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Reusable utility functions\nCollections\nStacks\nQueues\nSets\nData structures\nAlgorithms\nLibraries\nContainer types\nReusable APIs\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">For example, a stack could hold:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Stack&#91;int]\n\nStack&#91;string]\n\nStack&#91;User]\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">while sharing one stack implementation.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">15. The syntax you really need to remember<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Start with this pattern:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func FunctionName&#91;T constraint](value T) {\n}\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Example:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Print&#91;T any](value T) {\n\tfmt.Println(value)\n}\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Or when comparison is required:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Contains&#91;T comparable](items &#91;]T, target T) bool {\n}\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The important pattern is:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;T constraint]\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">where:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>T\n\u2502\n\u2514\u2500\u2500 type parameter\n\nconstraint\n\u2502\n\u2514\u2500\u2500 tells Go what T is allowed to be\n<\/code><\/pre>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">16. Mental Model<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Whenever you see:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;T comparable]\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">don&#8217;t make it complicated.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Read it as:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\">\n<p class=\"wp-block-paragraph\">&#8220;T represents a type.&#8221;<\/p>\n<\/blockquote>\n\n\n\n<p class=\"wp-block-paragraph\">Then:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>items &#91;]T\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">means:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\">\n<p class=\"wp-block-paragraph\">&#8220;items is a slice of that type.&#8221;<\/p>\n<\/blockquote>\n\n\n\n<p class=\"wp-block-paragraph\">And:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>target T\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">means:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\">\n<p class=\"wp-block-paragraph\">&#8220;target must be that same type.&#8221;<\/p>\n<\/blockquote>\n\n\n\n<p class=\"wp-block-paragraph\">So:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Contains&#91;T comparable](items &#91;]T, target T) bool\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">means:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\">\n<p class=\"wp-block-paragraph\"><strong>Create a Contains function that works with any comparable type, where the slice and target use the same type.<\/strong><\/p>\n<\/blockquote>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">17. Generics in one picture<\/h1>\n\n\n\n<pre class=\"wp-block-code\"><code>WITHOUT GENERICS\n\n&#91;]int     \u2500\u2500\u2192 ContainsInt()\n&#91;]string  \u2500\u2500\u2192 ContainsString()\n&#91;]float64 \u2500\u2500\u2192 ContainsFloat()\n\n\nWITH GENERICS\n\n&#91;]int      \u2500\u2510\n&#91;]string    \u251c\u2500\u2500\u2192 Contains&#91;T]()\n&#91;]float64   \u2518\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">One implementation.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Multiple types.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">18. What \/ Why \/ When \/ How \/ Where Summary<\/h1>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Question<\/th><th>Answer<\/th><\/tr><\/thead><tbody><tr><td><strong>What?<\/strong><\/td><td>Generics let functions and types work with multiple data types.<\/td><\/tr><tr><td><strong>Why?<\/strong><\/td><td>To avoid writing the same algorithm repeatedly for different types.<\/td><\/tr><tr><td><strong>When?<\/strong><\/td><td>When the logic stays the same but the type changes.<\/td><\/tr><tr><td><strong>How?<\/strong><\/td><td>Declare a type parameter such as <code>[T any]<\/code> or <code>[T comparable]<\/code>.<\/td><\/tr><tr><td><strong>Where?<\/strong><\/td><td>Utility functions, algorithms, collections and reusable data structures.<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">19. Three things to remember<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">If you remember only three things, remember these:<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">1. <code>T<\/code> is a placeholder for a type<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;T ...]\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Think:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>T = some type\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">2. A constraint controls what T can be<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;T any]\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">means almost any type.<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;T comparable]\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">means types supporting:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>==\n!=\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">3. Generics are useful when logic stays the same<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Instead of:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>ContainsInt\nContainsString\nContainsFloat\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">write:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Contains&#91;T]\n<\/code><\/pre>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h1 class=\"wp-block-heading\">Final Takeaway<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">The core idea of Go generics is extremely simple:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>Same logic\n+\nDifferent types\n=\nGenerics\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">For this example:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>func Contains&#91;T comparable](items &#91;]T, target T) bool\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\"><code>T<\/code> changes:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>T = int\nT = string\nT = bool\n...\n<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">while the <code>Contains<\/code> algorithm stays exactly the same.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Once this idea feels natural, the more advanced parts of Go generics\u2014<strong>generic structs, multiple type parameters, custom constraints, type sets, and <code>~<\/code> constraints<\/strong>\u2014become much easier to understand.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>1. What are Generics? Generics let you write one piece of code that works with multiple types while keeping Go&#8217;s compile-time type safety. Suppose you want a&#8230; <\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[1],"tags":[],"class_list":["post-1092","post","type-post","status-publish","format-standard","hentry","category-uncategorized"],"_links":{"self":[{"href":"https:\/\/www.devopsschool.com\/tutorials\/wp-json\/wp\/v2\/posts\/1092","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.devopsschool.com\/tutorials\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.devopsschool.com\/tutorials\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.devopsschool.com\/tutorials\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.devopsschool.com\/tutorials\/wp-json\/wp\/v2\/comments?post=1092"}],"version-history":[{"count":1,"href":"https:\/\/www.devopsschool.com\/tutorials\/wp-json\/wp\/v2\/posts\/1092\/revisions"}],"predecessor-version":[{"id":1093,"href":"https:\/\/www.devopsschool.com\/tutorials\/wp-json\/wp\/v2\/posts\/1092\/revisions\/1093"}],"wp:attachment":[{"href":"https:\/\/www.devopsschool.com\/tutorials\/wp-json\/wp\/v2\/media?parent=1092"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.devopsschool.com\/tutorials\/wp-json\/wp\/v2\/categories?post=1092"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.devopsschool.com\/tutorials\/wp-json\/wp\/v2\/tags?post=1092"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}