Monster shadow

VIDEO

C# Generics - Put anything in me baby

Description:
C# generics allow users to define classes and methods with a placeholder type. This provides amazing code re-usability while still retaining type safety. In this video, I'll teach you what generics are, how to use them and provide a few real-world use cases to get your head around them. I use game-like examples so you can see how you would use generics in your Unity development 🎮 ========= 🔔 SUBSCRIBE: https://bit.ly/3eqG1Z6 🗨️ DISCORD: https://discord.gg/GqeHHnhHpz ✅ MORE TUTORIALS: https://www.youtube.com/tarodev 0:00 What are generics 1:20 Writing a generic class 11:36 Generic Type creation 15:13 Generics and Interfaces
ADD A COMMENT

Rebonds d'histoires
thanks for this tutorial, really clear, as usual !
Andrzej Kułakowski
Useful stuff, and when it comes to archers, then there is the hooded man ;)
geniusforever
Hey! I recently found your channel and must say this channel is blessing. Also your art style is fooking awesome, it would be a another blessing if you do that kind of art tutorials
Tarodev
I'm honoured you would like me to do an art video, but I absolutely feel like an imposter in the art world. Are you talking about all the little mascots I drew?
Ahmet Emre Odabaş
Tarodev amazing videos brah keep it up its so fun to watch also teaches a lot ^^
Shiro Surfer
Genetics generates a function for each type it gets used if I remember correctly right? Kinda like syntactic sugar
TNothingFree
Great tutorial for beginners!. It misses few concepts that are important to talk about when teaching generics: - What is the difference between T and object - Why not use ArrayList? - What is a generic type T - How it's essentially different than a regular class type (Like array of objects?) This is a good point to talk about meta-programming, How a generic type looks under the hood. - covariance and contravariance in generic programming. A good place to look at will be Clr via C#, explains very well what is a type and a generic type.
Basic Dog Trainings
Thanks Taro, for C# Generics today I learned more from you👏[Battle King
Soundy M.
You had me @ dark souls <3
Toni
I love your stuff, just found this chance a few weeks ago, have you done any working with making UIs work with arrow keys only?? Like if it were an old fashioned computer?
ewwitsantonio
really useful! thanks!! also got a good laugh out of "nipplebutts" hahah
Eduard O
🤣🤣🤣🤣
Skull
Great video! This reminded me of one of the problems I thought could be solved using generics but I couldn't. Imagine using ScriptableObject architecture similar to the one described in Unity learn videos, where you store your variables as IntVariable, FloatVariable SOs and reference them in your classes. Now lets imagine UpgradeData class which would have to take either of thees types as a single variable - UpgradeValue. But you can't do that with generics because you have to define type at compile time. Any ideas on how to solve this? Not much info on the internet.
Alifarhad Ali
great work keep going
Burgerizza
just found out about your channel from a certain video that has absolute random numbers as examples and I must say I'm really digging into your clean video format, deep explanation and occasional dad jokes. Subbed and will hope for the channel to blow up soon.
Tarodev
Pure random numbers ;)
Enrique Barbosa Oliveira
your videos are very good, they are helping me a lot in the creation processor of my game. I spent 1 year studying to be able to make a game, now with some of your videos I managed to progress much faster. if I made a video showing my project would you see? I'm sure you'll be surprised by my idea.
Tarodev
These are the comments which make me feel good about what I'm doing. Yes I'd love to see your work
Billy
Thanks!
Pavel Tsarev
Why you are using void PingMap<T>(T inputObject) where T : IPing{} if you can use the way w/o generics void PingMap(IPing inputObject){} ?
Cronoo
Best Tutorials on the net xD
ala slipknot
I think everyone agrees that we need more *generic* tutorials outside of the usual game dev ones. (HAH!! see what i did there !?)
Twin-Stick
The wrongness in this title is just perfect 👌 🤣
SEE ALL COMMENTS


Transcript:

hello welcome so in this video i'm going to be teaching you about generics if you
don't know what generics are chances are you've probably used them in the past at
some point for example uh if you've ever used a list before and as you can see
this is in the system collections generic namespace you might have noticed
these angle brackets and that is because list is a generic class it allows us to
define the type that the collection is going to be so for this let's use string
and let's uh just call this games and this is going to be equal to a new list
of string so then down here we can say games dot
add and as you can see it is giving us
actual type safety here it is saying that it requires a type of uh string so
if we just try to put in a number here uh it would say no that is incorrect we
need a string so let's put in a game uh dark souls
cool and then we could make another list down here where we would in fact use an
int so uh my ins
i don't really know what a cool int list would have been and down here we can say
my ins dot add
and then as you can see it's now giving us the type safety for an integer so we
can say 69 excellent so to understand this a little
bit deeper let's create our very first generic class so as you can see i've got
just two files here program and declarations so this one's the program
and this one's the declarations i just figured i'll keep them separate it will
make it nice and neat so over here let's make a class and this
will be called uh generic class
and now this is where we put our angle brackets
so here we're going to say that there needs to be a type of t now t is just an
alias and it's convention in c sharp to make your first uh generic alias t just
like its convention in your for loop to put i as the first iterator
so and then you could go to like u and so
on you can have as many generic types as you would like in this generic class
so that's the only difference to make a generic class compared to a normal class
just adding these angle brackets and putting the the alias of your of your
data that you're going to put in so now
let's actually store what this data is going to be so we can
say public type of t and this will be data
so now over here we can actually create this class this generic class that we've
just made so let's say my class is equal to new
generic class and as you can see now we can now put in our own type into this so
let's call this a string cool so we have just made our own
uh generic class in the same way that list
creates theirs we've got our class name and then the generic type that it takes
and if we just deconstruct this list class here
we will see that they do exactly the same it is a list of type t
right list is just a generic class that is provided by c sharp but they're
using generics in the same way that we're using generics so that's cool
and now here we've got our little field here of data we can say my class
dot data is equal to and as we're using a string here it will say that data is
of type string so we can put in wobbly
cool this is a little bit messy so we could actually add a constructor here
and in this constructor it will take a type of uh data
and then we can just set our data is equal to data just like that so now
instead of doing it like that we can just directly say right in here
wobbly so now we have a generic class with a
constructor that actually takes the type of t into it
and of course if i change this to inch that would now say no this is a generic
class of int and i need an uh an integer excellent now generics is not just
limited to a class we can actually make a generic function
so we could do void
let's call this function print maybe and it's going to be of type
t and then in here it's going to take type
t and this will be the input and now let's uh
console.writeline and this will take in input
so now this function can take in any data type and then we can print it to
the console so let's try that let's say print and
this will be uh let's just put in an integer
now if we press play here we'll say that it prints out 420
and we can reuse this function easily with even a string so this will be let's
say a loop hero and then even further we could
let's say we had a class here public class
hero we could even do it with a
new version of this hero we can use this same code for everything
so let's try that there we go
so obviously when there's a string or an inch there's special logic in those uh
in those value types that behave differently when you print
something out our hero doesn't so it's just going to
print out the name now just imagine this was not just writing a line say say it's
doing something a little bit more complex right uh you without generics
you may have had to write a function for integers for uh strings and for hero and
all your other classes and structs right but with generics you can now reuse that
for all your different types okay excellent so
let's actually uh remove this function and let's actually put it in
this this function we don't actually need this we don't need this because
we've already got the thing that we want to print we're just printing data
oh yeah so we've got this generic class it's got
this function inside of it now and now we can say here my class dot
print and the output will be expected it will
just say wobbly as that is we're using a string here as our generic type
so being able to send anything into a generic class or function uh
is great but it can also be limiting like it's actually too generic what if
we have a uh in our hero class here we've got a
public void attack function and let's also say that it's got a
public uh inch damage and also a public string name
right and then this attack function will just say console.writeline
and it will say our name
did damage
damage okay so now we've got a hero here with a
name and damage and there's a function on it and it just prints uh this hero
did this damage okay so let's actually rename this
generic class let's actually call this like uh hero
helper or something like that okay so we're making a little bit less generic
now so don't get confused this is uh not the actual hero right our hero class is
here this is a hero helper we're we're putting our hero into this as the
generic function so let's just move this just so we've
got a little bit of extra room here so let's say
from this hero helper i would like to force my hero to attack so we could have
a function here called force hero to attack
and what we want to do is we want to make this data which is going to be the
hero right uh call this function attack on this hero class
because we've sent in hiro as the generic type
but there's a problem as this is so generic right it doesn't know what it is
this this t as far as the compiler knows is an inch
right it could be a a dictionary a key value pair it could be a list it could
be anything in the world which means it doesn't know
what uh values and methods are actually on this
thing so as i said being able to send in something anything is good but it's also
a constraint so we need access uh to this hero right so
and also just to iterate this fact a little bit more let's say we've got uh
a mage class right and that that inherits hero
and let's say we've got a warrior class
and let's say we've got uh an archer and a million others right say we've got
a million other classes all inheriting from hero and then let's delete some of
this stuff i'm going to create my hero up here so
var warrior equals new warrior so now i've got my warrior
and also i'm going to set its name to tarot dev
and it's damage to 420 powerful okay
so we've got oh that should be a lowercase
cool and now i'm going to make uh my hero
helper so i'm going to call this helper equals new
hero helper and i'm going to say this is going to be
of type warrior and it is taking in my warrior
so we're using this in the same way that we used our previous generic class we
we're giving it the type that we want it to be and then we're actually giving it
the value and now obviously we can still say
helper dot print and this will
print and i'll just demonstrate that it'll print the name of the class
warrior cool but i want it to do more than that
right this is a hero helper i want it to i want to be able to force my hero to
attack so
as i said previously it's great being able to put in anything to this generic
class but sometimes it's a limitation so this is where constraints come into it
generic constraints so we can say uh hero helper take some
type of t where
t equals
a type where we're saying we're confining this generic method to have to
use a specific type this one will be of type hero okay so now it doesn't matter
if it is a warrior a archer a mage or even just the hero itself uh which we
shouldn't let let's let's make that abstract
that's beside the point of the tutorial but obviously you wouldn't allow uh your
base class to be initiated as an actual hero
so this function is just saying as long as
t is of type hero i'm good to go and the benefit that this
gives us is now we have access to
the hero methods here so now we can say attack
and before it didn't know that it was a hero so we didn't have access to that
function and now on the flip side as this is requiring a hero we now cannot
use an interior
right we can't use an in here because this is not of type
hero so this allows us to
be more flexible with what we do with our generic
methods and functions okay so now something a little bit more
advanced let's make a factory method which will
actually generate create these heroes for us
all from just one function so let's say this is going to return type of t
and this will be our hero factory and this will be a generic function so
type of t and in here let's actually take a
parameter that we would like the hero uh to be called
and this will be where t
is of type hero let's give ourselves a little bit of room here
and close the brackets now in here we
actually need to create this t right we still don't know
what it is but we need to actually generate the t
so let's say t new hero is equal to
t whoops nu t
parentheses now this is giving us an error
uh and that is because although we know that it is type of type
t we don't know if these classes that this uh t here is going to be
we don't know how it is constructed right this mage here could have a
constructor which takes in uh inch for its damage
right whereas the warrior might not and then
the archer might have a constructor that takes five arguments so
we don't know the see the compiler won't know for sure so it could actually throw
a runtime error right now we can fix this by adding an additional constraint
to our generic method and that is to say to
tell the compiler that whatever we send into this function it
will have a constructor
with no parameters okay we are saying that this function will only accept uh
types where the the class has no uh parameters in its constructor
so now that we've uh gotten rid of our squiggly here we can actually return new
hero whoops new hero and there is our generic function so
let's try this out let's say var uh archer
equals hero factory and let's send in archer
right and then it's asking for our hero name ah and i didn't actually fill that
out so as we know that this is of type hero here we can say new hero and it has
a name and we can say hero name
what's in the archer's name i don't want to do legal asses like
everybody does that but uh the show must go on legolas and i bet
you i spelt that room legalize
whatevs sorry uh so this works because archer has
uh well no constructor but also that it's got no parameters in the
constructor if we wanted to change this to mage
it's going to say no you are you have told us that the object
that you're trying to construct has a constructor with zero parameters all
right so we can actually now in a generic function generate
objects as long as
the type that we send in has a parameter less constructor cool so as you can see
generics can be super powerful they can make your
code dry af by allowing you to reuse code snippets and really you've almost
learned everything there is to know about generics like i do want to show
you one more thing so we've got our heroes here
cool but let's say we've also got uh i don't know uh a chair
right we've got a chair and we've got a uh
manager all right so this could be a furniture
store uh it could be a game too because heroes need chairs uh
and a manager of an in or something i don't know
and these are all super unrelated objects and none of them can really
derive from one another right like i'm not going to make a chair
implement hero because that would be stupid uh
but if someone makes a game of that you're gonna give me credit at least
all right so i'm just trying to think of a scenario uh say you're
say you're making an mmo right and let's actually change this to uh the the anvil
so say you're making an mmo and uh you're you've got a mini map and let's
actually change this to be more relevant let's call this a mailbox
right let's say all these things have a shared
uh job and that is to ping your map okay we
obviously can't uh derive anvil from hero okay that wouldn't make sense so
let's make a public interface and this will be of iping
and then this just has a required function called ping map
like that okay so then our mailbox will implement
i ping and it will have that function there and i'm not going to actually
implement it but let's just assume that that one that map shows a map icon on
the minimap right and then anvil will do the same
and hero will do the same let's just assume that like it shows the class icon
on there this could possibly be overridden or something on these derived
classes so now these seemingly completely random
objects we can now write a function that can
action any of them so this will be of type this will return type void and this
will be ping map and this will take in a type of t
and this will type the actual data will be t so let's just say input object
and our constraint here will be
where t is
i ping and now we can call input
object.pingmap so now an anvil a mailbox and a archer
warrior mage like any type of hero can we can now reuse uh one function to
perform different logic on all of them right and they're all actually doing
different things they're showing different icons like if it's a hero
it could show up in red or it could show up on uh green if you're in a party or
something you know so that's how you can mix generics with
interfaces to create like true code reusability
so there it is uh that's generics i hope my use cases were nice and easy to
understand i probably should have gone over this one in my head a little bit
more pre-planned it but i think it turned out alright if you learned
something or if you enjoyed the video subscribe let me know in the comments if
you enjoyed it and uh if there's a topic that you would like me to cover maybe
you're having trouble with something also if you're feeling lonely come over
into my discord have a chat we'll talk the uh let me know about the game
that you're making or something and yeah i think that's it so i'll see you in the
next video ciao