What’s new in C# 13 | BRK186

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
Well, well. Hey everyone. Hello. It's the last day of Built and it's the first session of the day. Are you all awake? Can you say that loud enough that those who aren't will become awake? You have to overcome. Who's awake? Yeah, there we go. So what's new in C# 13? Well, here's something that's not new. No, not new at all, sorry. We are the speakers made. Torgeson is me. I'm an architect at Microsoft and I'm also the lead designer of this little programming language called C. And my name is Dustin Campbell. I'm a Principal Software Engineer on Net tooling in general and also a member of C# Language Design. So I have two buttons, he has like 60. I have the keyboard. So you're doing the hard work. Just a couple of things. Householding, we're gonna be talking about C# 13, right? That's a new C# coming to release near you in November. C# 13 comes out with dot net nine. And we as always, we kind of lean into taking the C# that you already know, starting from there and just making it a little bit better, right? And out of a host of small, tiny and large features, we're gonna focus on about 3:00 today that are probably the most impactful to you. And the important thing about these is that there are things that you already work with, right? They're either language features that where we're making them just better, or they build on concepts you already know from existing language features. So there should be no big like explosion surprises in that sense, but hopefully you'll find it immediately. Useful. We hope so. Yeah. And we just about to get started. Dustin will switch to his desktop because slides. But before we do, you will probably have questions. We may or may not have time for questions in the room at the end, but we have folks on Pebble in the room. We have two other folks from the C# language design team. We have Fred and we have Jared and also online we have Kathleen and Cyrus. So they will answer questions along the way and possibly throw one or two to us at the end if we have time to answer. And for those who are in the room or at build, we will also go to the experts area. We were officially scheduled, I think. At like 11. Yeah, we're probably head there a little earlier, so you can come find us and chat with us about everything we showed today. And we will of course have machines where we can go into the details of the bits we showing outside of today. If you want to Orient yourself about what's happening in C#, we have these nowadays. We put preview implementations of our new features gradually through the release cycle into the actual compiler bits. And so if you compile with language and preview, you know, occasionally a new feature will pop up and you can play with it just in your release bits. And as we do that sort of roughly In Sync with that, we also put new documentation articles out and that's the page that you see here. So depending on the level of engagement you want with C13, I mean, obviously there is some level of engagement cause you've come to this session, right? But this is a way that you can kind of keep kind of a higher level of how things are happening right now. It's actually this documentation page gets updated as features become available, right? The features we're going to show today, only one of them is available and it's on this list. But so this list when you go here right away, you'll immediately you'll say, well, this seems kind of short, right? And that's because these are some of the kind of the, it's almost always at the beginning of the cycle, these smaller features get checked in things that are kind of like pent up or didn't make it into the last release. And so that's what you're seeing here today. But this, this is a dynamic page. This will continue to update all the way into November. So you look at this page today, it's kind of boring. Yeah, C# 13 isn't that kind of boring? But that's just what's already done. If you go to the next web page is that's the compiler repo on GitHub. That's Roslyn, which is the name of our where we built C#, the implementation and we have a a working set. We have a list of of feature status and you can see that list all the way until you hit C# 12 there. Even seeing which versions of Visual Studio they'll become available and when. They're that's all stuff we are working on. Not all of it will make it into C# 13. Some of it is longer lead, some of it may not happen for various reasons. But this is just here, you can go and see all the stuff that we're working on, what's the status? And you can click on the links on the actual features and then that'll take you into the other repo which is C# Lang. So this is like really the engineering repo, and then this is the design repo. This is where the C# Language design team captures everything that we're working on. This is where people submit proposals and there's discussion that if you want to get involved at that level, you're welcome to. And they're wonderful meeting notes that Fred writes for every language, one meeting that we do that are just available to everyone. Yeah. So if the last page was how the sausage is made, this is how the sausage is like shaped. It's how it's designed, Yeah, OK. Enough. Enough we want code, so let's let's jump right into talking about the first feature. Here. Yeah, this is this is actually very representative of the code that we left you guys with last year when we finished up our talk on C-12. It's not exactly the same, but it's roughly the same kind of code and we kind of wanted to use this as a kind of a springboard into some some some new things. Yeah, we want to remind you of collection expressions. So we have a couple of those in here. This is the big hit of C# 12 in my mind. Yeah. And the point of collection expressions to remind you is you can put one of those and and it'll convert to pretty much any collection type you can think of. So depending on what the target type is, it'll build one of those. And the compiler has gotten really smart about doing the right thing for every given type. Yeah. And the right thing in this case because there's three overloads, which means it needs to pick one of those to produce something for. And in this case because there's one that takes read only span, which is, you know, this high performance struct that really we can do with no allocation. That's what it picks, right. And so it produces essentially a collection, you know, a a read only span that takes no allocation to produce. And then in the ad grades that add range method down here also takes a read only span. It's part of net one on the list of T APIs. And so it's just there's when it 4 reaches that, there's no allocation there either. So this is the this is the best for your application with regard to like kind of like hidden costs. And so so we select that one. So that's a reminder from last year, but there's also one of these overloads. Is of the params array. Params array forever in the language. Yeah, these are boring. These are from C# one. And but it does mean that we could take those square brackets away. And yes, now you can just you know if. You want to allocate then you can do that. Well, The thing is, yeah, now it now it will pick that the overload that isn't the most optimal. And you know, since actually since probably we got generics and we had our normal of tea, people have been saying why can't I just have a param signable? You know what? Because what they end up having is 2 overloads and innumerable T overload and then a an array overload. That's the params. Why can't the innumerable overload just be params? Precisely this is like the first language feature request of C# 2 after generics came in like. But now that innumerable of T is there, can't I do this? And and in C# 13 we can. So took 1111 releases, but we eventually do listen and yeah, and and you. Know you're not the we not quick, but we have sorrow and also we happen to now have this whole machinery for creating other types than arrays based on elements right from the collection expressions. So we can just go and plug that into Innumerable. Yeah, Now we won't select that, right? We're still going to select, you know, the original, you know, overload. We don't want to break the code by picking something different in this. Case it's just better by overload resolution rules, right? So. But if I, if I comment that out, surely, yes, of course that does in fact work and it picks planning rule. And again, this has some of those hidden costs, but that might be fine, right? Yeah, it's it is certainly more ergonomic. But if you really want the, you know, the high performance thing, like what was picked before with collection expressions, it would be really nice if you also had params of span and read only span. And that's another, it's more frequent, but very highly requested feature for people who are like want to avoid allocations and are at that level of of performance focus. And sure, we can do that. Right. And so then in that case, we will pick the read only span. And so again, now if we have in the libraries, when we add read only span params overloads, when you recompile your programs, they will pick those and they will suddenly just get a little better, a little nicer. And to remind you some of those API, they're already going in, they're not in the net 9 preview, 4 bits that just ship, but they should be there next time around. But that includes things like string format console, right? Fine, yeah, I just saw PR open in Winforms for like all of these, all the like system drawing API make sure that we have read only span params overload so that things can just be more efficient by default. Yeah, It becomes one of those features Steven Tope likes to show off so much where you recompile and everything gets faster, like in combination between their language and the and the libraries, adding these extra overloads, these params overloads, or putting the params on their existing span overloads. Yeah. So France is sort of the next turn of the crank of. Yeah. Cool. We were thorough. Yeah, that's good. Alright. Cool, let's try something else like this is. Was we did C# when we talked about like how there was a request in C# 2? Let's go into like C#. 3 chap. 310 releases ago. We are cleaning up. Yeah, one person at a. Time sweeping everything up, yeah. Yeah. So in C# three, I was around for the design of C# 3 almost from the beginning. So that kind of dates me. And that's when we added auto properties. And we actually had a big debate because we knew, we knew from the start that auto properties was going to be a problematic feature, right? It's, it's, it's great. It's a great shorthand if it does exactly what you want. But if you want anything ever so slightly different, you fall off the Cliff. Yeah. And you have to write everything out manually and it's like 3 * 4 times as much code. It's the worst, right? You gotta clear backing field and now, OK, now I gotta, you know, take these semicolons, turn them into curly braces and write code in there. It's. It's a mess, so we were very much on the fence, but in the end we were like, this is so useful when you can use it. We're gonna put it in anyway and we'll see what we can do about the Cliff. And here we are, 10 versions later. Yeah, we are doing something about the. Doing something about. This we've tried in the past to kind of limit the Cliff, right, We did like get only out of properties we've done, you know, even a knit could be looked at as a way of doing dealing with that. We added the initializers, these weren't there and so. You couldn't do that. So we've done things to try and make it a little easier, but this time we just said, you know. Let's just fix this. Let's just do away with the Cliff, so. As an example, let's say that we just want to do a tiny little bit of thing, your tiny little bit of work in the setter. It's this is all alright. We just want to like we want to trim the white space off the ends of that name that comes in. Absolutely. This is what this is what always you always want to do, right? You just want to say, ohh, I want to say, you know, do something with it, but say like, okay, value dot take that and trim it, right? I want to then push that into something and in C13 now I'm going to warn you, there may be some squiggles here because this is under active development. Yes, but Chuck is working very hard and he's probably listening, right? Now, right, Chuck? Right, Chuck? Yeah, and so you will be able to assign to a new keyword called field. Yeah, field is simply is an A name for the generated backing field that you can use inside of the of the accessors. And it's actually just like you see value is is coloring blue there. And it actually for for our purposes today, let's just say it's a contextual keyword. It will be use your imagination filled as blue. Yes, and Squiggle is not there. Field will be blue, field will be a keyword only inside of property accessors, right contextual. Everywhere else it would still be an identifier. Right. This one's taken us a while. We actually showed it last year and it didn't make it into C# 12 and it was, it was heartbreaking. So we really want to get it this time. So before we talk about like anything else, just let's sum up Auto properties now can have bodies. Yes. As long as as long as the body is still left unimplemented or somebody mentions field, it's still an auto property. We'll still generate a backing field for you and everything you know is as you expect, except you can get it that in in your optional access or implementations. Now the goal here is to be able to kind of encapsulate that property, right? Not to have this like field just dangling out there that maybe somewhere else and maybe maybe it's a really large class and somebody messes with it some other, you don't want that, you want to protect it. And so, yeah, so that was the goal of auto properties. And now they really do remain. There's still auto properties. Yes, they're still shorter and still protect the backing field, but hey, you can already say field today. Right. Yeah, let's. So let's so. OK, first of all, do you like this feature? You're gonna use it alright. I think people will use this immediately. OK, I wanted you to be happy about it first before I I come. I told you the bad news so you could. There will now be code that's legal today, like if you happen to have something called field and scope and you're referencing it in a property, that reference will now be a keyword instead. And so this is a breaking change that's in C#. That's something we haven't really done before at this scale. It's not like a massive, but it's still like people will be affected. By this is a student class, so it's perfectly reason to have a field of study as a student, right? And what we usually do and when we have that situation, that design clashes with existing code, we say, oh, we're going to make up some really arcane weird rules and then they will be in C# forever. So that if somebody adds something called fuel, like way, way, way over there, then the meaning of code over here will silently change, right? That's how we've kept backwards compatibility. And this time we're like, ohh, this hurts in our stomachs. We want to do something different. We want to actually do the language feature properly and instead of having a forever degraded experience with with the new feature, we want to do, we want to give like a a small short term inconvenience of say like you may have to change your code a bit. Yeah. So the way we do it is that when you get the new compiler, you're still in in a previous version of the language, probably most people have said. You'll most people you'll install Net Nine SDK your program. If it was it was it was targeting NET eight, then it's still technically using C# 12. Until you actually use NET Nine, you're you're not using C# 13. Yet. But now the compiler will give you diagnostic saying, hey, here, here and here you have code that will change its meaning in C# 13. You're not there yet, but it will. Do you want to fortify your code against that? Yeah, here's here's a fixer for that. And what that fixer will do is very, very simple. It'll just use another feature of the language has been there since C# one where you can put an AT symbol in front of a keyword. You can actually do that in front of any identifier today, but but it really it's there so that you can have a keyword, have an identifier with the same name as that keyword and you can disambiguate it. And that's what we're doing. We're just doing it in advance. Yeah. So in these cases you will get tooling help and this is the fix, right? Just put the add sign in front and you're back to it working both in previous versions and still in C13 the same way. So that's how we can, this is the first time we tried this, the tooling around this, the exact experience. There might be some Rd. bumps help us with feedback because we may want to do this again. Occasionally we may even want to go back and look at like VAR or or Descartes and say, can we make those a little better? They're they're kind of confusing today. So breaking changes, we're going to try to manage like these very limited breaking changes that have very easy fixes and give the language a little more freedom to do the right thing. OK. You're OK with that? Alright, OK. Thank you. OK, so it's the first two we did params collections, we did field access in auto properties. Now I want to show we want to show a feature that really we've only ever shown in slides. We've we've shown it before, but but more of a vision kind of thinking. Now we have some bits and as I always like to say, they are indeed magma hot, but they're like surface of the sun hot. This time it's not just from a feature branch that's not in Maine. They're actually this is. These are built. These bits are built from an open PR, so the. Standard rules of physics no longer applying. You know these? Bits. Yeah, yeah, I'm actually gonna roll this back a bit so I can. We got them last Friday. Yeah, built off of an open PR on a feature branch. Some things won't look, some things will be cheating a little. Some things won't work yet. We'll try to point out where if things will be better, but here we go. Yeah. And we are again building on C# 3, right? Fixing things for you in the past? No, this is actually building on a concept, right? How many people? I mean, everybody does, but how many people write extension methods to use in their code? Yeah, yeah, they become extremely popular. I mean, when we introduced them, they were about query expressions and links so that we could transform those expressions into selects and wheres and all of that. But people write them a lot. And the reason I think people write them primarily, there's a, there's a compositional kind of kind of architectural sorts of reasons for doing it. But also it's just discoverable, right? There is real power in being able to press dot and getting everything here and getting this, this parse as Jason down below. That's in Intellisense and it's there because I've declared an extension method right there, right? So there's real power and discoverability when you're writing code. And also there's kind of like this idea of being able to write little DSLS. We do all those sorts of things with it. So they're just very, very powerful and became very popular. Yeah. The only problem is it only the only thing you can sort of fake is instance methods. Yeah. Any other kind of member you can't do. And even in C# 4, even the very next release, we were hard at work trying to see if we could make extension everything like if we could make other kinds of extensions. And the syntactic paradigm of like hijacking a static method just didn't work. We let it lie. To age myself I arrive when C# four was in development yeah and they had already abandoned extension everything and moved on to like can we just do properties extension properties and eventually said it doesn't feel right and backed away. Yeah, so like we, this has also been on our minds for a long, long time. But so we needed to take like a step back and a new syntactic direction for extensions in order to uniformly scale to all the different kinds of members, at least ultimately that you might think of doing as extensions. And so in this example, we have a call of a static method. And so wouldn't it be great if we could like get to where we have a static extension method? Yeah, this is weird, right? You to add this, this parameter and all that sort of thing. And so it would be really nice if I could write that as an instance method. And if I introduce this new kind of thing that we call an extension and we can write that here, I can say this is actually an an implicit extension. Let's just do it right now. She's doing it. I'm doing it say implicit and extension, right? And then I can say 4 the type that I'm extending. So we're going to make an extension for string. OK, now this extension method, this old school C# 3 extension method doesn't make sense anymore. We should actually write that as an instance member O as if it was as if we're just augmenting that type in the four the underlying. Type almost as if you're writing a partial class we're inheriting. And that's still works and that's how with extensions. Ladies and gentlemen, we've recreated feature from 10 versions ago. You're. Welcome. We have recreated the syntax for that feature, but but again, it's not conceptually new. This is things that most people raise their hands and that was that was that was validating for this right that we're going this direction. So you just put an instance method there and it became an extension method, but you also have a static method. I have a regular static method here. Is that an extension static method? It may be so if I go then instead of again, it's the power of dot. Right now if I go to String as a type and I press this, you'll see that create identity is there as a static extension method, which is something you could not do before. Yeah. So now, so now you truly get that transparency of the thing that declares the extension methods. And it can just sort of appear as if those things are on the underlying type, as we call it. And we call these like the, I think the formal name for this this feature is extension types because you see really is a type declaration. Yeah, it has a type name and, and but it doesn't really introduce like a full new type. It just says I am that type with something extra, some extra functionality at it. You can't add like state, we don't let you do that. You can't override methods, but you can add extra things like with extension methods in a syntax that looks like a type declaration. I mean, you can see here I press dot again inside this method, this, this, this type. I have access to all the public members of string. I don't have access to like internals. It's not like I'm actually inheriting. I'm writing, you know, under the hood, you know, you can think of it as augmentation or if you really want to know, it's like writing a struct wrapper around it that that so, so it ends up being transparent 0 cost essentially. Yeah. And just just adds things also just to kind of drill home that we we have a scope here. We're in a, in a place where where when the members we have are kind of it's as if we're on string itself, right. And so you can see if, well, maybe you can't see, it's hard to see that that's actually grayed out because we don't need to say string.net. We can just say empty here because we're we're in the space of talking about string and its members, right. So name lookup works like that. OK, this is cool, this is cool. Let's play with this a little more. OK, I actually want to do some things with this so. There are other kinds of members. So let's let's take we now we're taking some this example here we're taking some Jason in a string and we're training it into Jason element so. That's there's customers. These are, you know, an array of objects that have names and orders, which are an array that has have descriptions. OK, lads, likes beans, rice and Pickles. OK, OK. That's cool. Let's let's dig into some of this data like this. Start traversing it. Yeah, delete this guy right here. And then we're gonna, we, we need to get the customers out. And we're we're using actually we're using system text, Jason. So it has its own particular API shape and I can walk up to that data property up there and I can ask for that customers element, OK. And then I could four each over that. So if you think this is cool, this is already there. This is not API, Yeah, still cool. But when in in system text, Jason, when you when you enumerate something that's at like this is still all of these end up being Jason elements. Yeah. And when you enumerate a Jason element, then it's going to be an array. You you call this enumerate array method. All of this is pretty much, I believe it's allocation free to do this work with Jason. And then we can pull out say like if we recall those customer objects had name properties. And so again, it's kind of, it's kind of tedious. It is tedious. I don't feel doing this. Now we have to say that you'll get string. Yeah, and I gotta I gotta not typing correctly. Yeah, if you string. If you had a typo in there just once, you know it goes. Yeah, this is, you know, it's very loosey, right? We're we're we're kind of working with loosely. Typed so I have an idea. Could we do like an? Yeah, I'm just pretending I have it now. We actually prepared. Can we do this? That's an move. Could we do an extension property to like get? Could we just say dot name? Yeah, that would be great if I could write. End this. Yeah. And just like it would just be there and that extension property does the unsafe work, but I just get, I actually just get a string back. Yeah. And I have chills and all that stuff on it. Yeah, so Magma hot bits mean, folks, that Intellisense may work against us. You're welcome to laugh. It's fine. It's expected. All that comes later. So. So I would declare an implicit extension. We'll just call it customer, right? And then we can put on here a name property and let's just oh, I should have copied that code earlier, but. You can write. It again I can write again, we can say this again, get property name and then get string and we get a little null ability warning. But you know what? We think it's there. We just work good it's there. Yeah, yeah, yeah. Override. We're good. Don't ever do that. Yeah, so. Well, we're doing weekly type stuff anyway here. Who cares? If it blows up, it blows up OK. But look, the squiggles gone. Works extension properties, ladies and gentlemen. Although I I think I might have spotted a problem, yes, because this is just an implicit extension for any Jason element, right? Customers is a Jason element, so I could do this too, right? And it will think that's fine. Yeah, but it'll blow up because that's not what we meant. No, this was is because this doesn't exist there. It's an array. Yeah, we're so close. Like we, we have this way of putting things on there. We just don't want to put it on all Jason elements. We only want to put it on some Jason elements. So how can we make an extension for just some some Jason elements? Well, that's where we that's where we get to. Why is it called an implicit extension? That's because it's an extension that implicitly applies to all values of its underlying type of Jason Allman in this case, right? But we could also make it. Go ahead. Yeah, we could make it. What? Any guesses? Yes. Listen. And now it doesn't. Right. And so now. So now we made it. We made it not work. Yeah, because it's just a Jason element, it's no longer implicit, right? So how do we address that? Well, in future bits, you should be able to do something, all sorts of things where we can kind of take a Jason element and kind of easily coerce it, implicitly convert it to yeah, customer in some way. So I'm, I expect, you know, we haven't exactly done all this yet, but I expect I should be able to do something like that and then turn it into a customer, which does work, but that kind of fails down here, right? So. And that's should be clear. That's just because of the bits we have right now, right? This is This is how it's supposed to work. Like this surface? Get it, Jason? Yeah, I get a Jason element. I choose to put on the glasses of customer and view it as a customer by converting to the extension type called customer. Here it really comes to use that. It's a type. We can we can implicitly convert to it. Now we're viewing it as a customer and now it has a name, except we can't yet. So we cheat a little. Yeah, So we're going to cheat and I'm going to tell you that we're going to cheat right up front. We added in our own little extra extension method, our own enumerate array that does the coercion. This is none of the conversion for us and he and so but expect that we'll be able to do that in in in final bits and said I could type var here if I wanted to keep that. And and it's still customer. Do we want to try to run this just to see? That yeah, we should do that. We should ignore the man behind the curtain kind of thing, yeah. OK, so, so while that takes a while, maybe, sorry, just note here, explicit extensions essentially there are, you know, they're lightweight type the the thin wrapper that you can put around something else. In this case there's something else that we're putting it around is weakly typed data represented as Jason. And but you can imagine it all in a lot of other cases you want to look at certain data with specific, with a specific angle, with specific enhancements without that applying to all of that data that are underlying type. And that's what's happening. Here now I want to point out that it did take a long time to build and run and I want to address that. Just just know that that is because these are built bits, they are not optimized in any way. And also the way we kind of bring that compiler in time tends to be a little slow. First run, Next runs should be faster. OK, so let's let's continue some fun here. Let's OK, so we actually we have a week data model in Jason. Let's write a strongly typed object oriented overlay for it. Yeah, so we have using an extension for customer. Yeah, let's do one for our order. You can actually copy paste the other one. All right, that seems so sensible. I know, you know I am the architect. I'm out. Don't let me near that. Keyboard. Alright, so order we, if I remember up here order was order had just a description property. Yeah, OK. And so we can kind of do the same thing here. Whoops. And then I will go ahead and type this 100% accurately. So nothing fails, OK in there. And so now we have that. But what we also want is that customer has an array of orders, right? So let's go ahead and add another extension property here. Making an innumerable of order. And then we can do a similar thing to what we did above where we can say get property orders. And I realized that I've forgotten the name of that property. Which one get all sorts of embarrassing squiggles. It's OK, I I don't feel bad. You guys do It's cool. Yeah, alright. And we can pick our our our special little enumerator array that we won't need in the future. And now we have an orders property. So I could then take this customer and I could forage over say order in customer dot orders and I could write, you know, something like we'll say so and so ordered order dot description. Yeah, right. And we should be able to run that and hopefully that goes a lot faster. See, I told you, there you go. We'll just fine. So. This is cool. This is cool. It's like TypeScript, right? Yeah. Anybody here use TypeScript? You know, JavaScript, All objects have just dictionaries. They're like our JSON elements here, and they just put types on top. And you know, most of the time it works out. I and this is kind of similar. And you're like, but this isn't really strong typing, but it is to some degree. Yeah, right. Because a, you only have one place where you to make the typos, like you're abstracting out where you're actually giving those strings again and again. And B, you have now you have this model that through Intellisense you can get, you can discover and and verify that the code you write matches the structure you expect. Now, if the data doesn't match the structure you expect, that's a different problem. But if you up front say like this is what I expected it looked like the rest just falls out and that's actually still kind of. Cool. It is cool. You could even write like a query expression, keep it with C# 30. You could query over this data, yeah, just with like with normal link to objects and it's fine. Yeah, so and, and just to you know, OK, is it a little tedious to write these? But they're not actually. These explicit extensions aren't bad to write, but you are like writing all that gunk in, in all the implementations and it's pretty repetitive. You could imagine a source generator doing that for you after looking at like some Jason schema or maybe some examples of the JSON you you were expecting or you know, TypeScript types that somebody already wrote. Like you parse those up, you generate out your explicit extensions and you know, you take your route Jason element and you implicitly convert it to like the type you created for the route. And from there on you just statically type without any effort. It's not just like we statically type. You get this free like literally like cost free static. Types. So we think there's a lot of, there's a lot to this scenario too about like the the the strongly typed shims, if you will, over weekly type. Yeah. So we can do these cool things, but also, yeah, these will be like the things you use extension methods for today. That discovery. This is the same kind of thing. You get that discovery on dot. So I think it's going to go. I think it's going to go far. You can use this, you think? Yeah, yeah, alright. Well, if you do, if you're still on the fence, we have a couple of other ways to show you. Right. So just just to kind of run the gap, the gamut, we haven't we haven't shown an extension index so yet, yeah, here's here's an implicit extension again. So it applies to all you want 60 fours. And it's just this idea, you know, I have this, this unsigned 64 bit number. Why can't I? Why can't I have an indexer that accesses every bit of it as you know and get you know? As a pool and I could tweak it, right? That would be cool. That'd be super bad, and we don't need to get too much into the implementation of it. Just witness here that there is yeah, an extension indexer that actually like if you go write. It it, I, I could say like we could do things like say, well, OK, take like bit, I guess two and we could say like grab bit zero and or together bit one. And maybe just take this bit this, this right line and copy it down there. Or we even have a reverse method on here, right? That just and again, this is an extension method that just appears as part of this. And uses the indexer for it's implement. Even uses implementation of this. Here's a static extension property. Yeah, but we could say, OK, let's just reverse those guys. Whoa, whoa, whoa. Number equals numbers. And this one I would ignore the lack of intelligence. Alright, and I can paste that again and if we run this code. You're gonna see some big numbers. You're gonna see some big ones and zeros, which is very exciting. Yeah, I understand that again, but but you can see that. Yeah, OK. You can clearly see you can get out your. Very closely right here was it bit it index, index bit index two and we flipped it. Yes, yeah, this, yeah. So, and if you're just very quickly briefly look at this code example and we'll move on. But inside of the implementation of this index, here you see we say this dot value and a few. Places right we're this is our hacking. We're hacking like you can do because this is an extension of of of you along, right? You would be able in the future to just say this and you're talking about the Ulong with its extra and. They should be able to do do it exactly like this today. The bits don't work, but they're getting there. Julian is working very hard and that's why I, you know, I invoked his name. He's probably also out there watching her. Yeah. OK, no, one more, one more extension. Example. Yeah. And one more and this one I think is that's a little more off the beaten path, but it's, it's not, it's something that you might not expect. Yeah, this is like, OK, so using aliases right there, they're so cool. We all love them right now. They're disappointing. Is yes. They're disappointments, Yes. And like and we get feature requests all the time. Can you make them better? Can you make them better? So I would like this one to be generic. Friends, yeah, we get this all the time. We have talked about this ad nauseam. Can I ever do this? And then I could pass it in here. You could even have like constraints. Oh, yeah, we could add a constraint. And like, this raises all sorts of questions. But then it also has a lot of, I would say, ergonomic issues with using it. Yeah, right. Because it's a using alias, so you can only use in one file. What we fixed that. We could make it global. Make it global. But then what if you wanna like, export it from your assembly? Now, Now we need to be able to say like, OK, it's it's gotta be public. And at this point, at this point, we've reached a little bit of silliness, right? It just seems like we're, you know, using as buckling under the weight of what we'd like to be able to do. And maybe it's not the right feature. But hang on, we just saw explicit extensions a moment ago, and they're really just another name for the same type, but with some extra members added, right? Yeah, an alias. So what if we do that, but just don't add any extra members? That's an alias, right? That's just. What? OK, I'll just replace using with explicit extension. Explicit. Explicit extension. That's going to be fun to type. All right? And and then we can say oh we need 4 instead of the equal. And four, and we don't allow the semi colon yet. That's just a bit. So I think, you know, type declarations can have semicolons now this they'll just be like. We'll put curly's for now and and if. Of course, I can come down here now. And so I've declared an extension that does take the generic parameter, propagate it at a constraint. Yeah. And I'd come down here where I do get, you know, the parameter help in the generic list. And I can say, well, I want that to be like, you know, the string data item and and so then and I got to close that extra extra angle bracket, you know, 2 angle brackets like that. They always make me. Do that every. Time. But then you can see here right that that in fact it's calling the add method and data set itself is an explicit extension of T where T is constrained a data item and T is actually filled in with a generic argument string data item. So OHH. And and by the way, don't you just love how using alias make you put the full name of every type? Ohh yeah, we don't need that anymore, right? This is just another an ordinary type declaration. It can use, it can use the imported names, right? So there you go, you have better aliases like just out of. They just fell out of this feature. We were doing like, ohh, we we don't need to do more about using aliases. We have a better feature already. Yeah, all those places where you might say, oh, I gotta go write a new class, I gotta go write a new type, right? These are just these transparent, beautiful rappers that make these that are very cheap and make these kinds of scenarios just light up really easily. So with that we were actually through and we have a good 5 minutes left. We have time for one or two questions. I want to 1st go to our pupil folks and see they don't have. Any shaking their heads. So if anybody wants to ask a question at either of the mics, one or two, you're like, ohh, I didn't know this was going to happen. I didn't think of a question. Yes, somebody who's close to the mic and then meanwhile somebody else can sneak up. M2 go for it. Thank you. Great stuff guys. Hey, could you go back to your bits example the previous one? Absolutely. Are you going to poke it like the the the sneaky things we did? No, it doesn't. You give a name to your extension type bits for you 64, but you never used that name anywhere. Is it possible to leave it off? We discussed that. The reason it can be nice to have, you know, with old fashioned extension methods, occasionally they clash and you have to disambiguate. And the way you do that is you call it as the static method on the type where it's actually declared right. So you have a fall back. And we figured it's good to have a name for that same reason that you can in fact go and coerce your thing to that type you. Could cast it to bits and then make sure you're calling the right thing. So the little thing here is that implicit extensions are actually also explicit extensions. You can use them as the type just as you could with the explicit ones. They just additionally show up by default on the underlying type. So that, so using them as a fall back seems useful. And so we haven't really gone to the can you just leave them off? But maybe I think it's it's kind of likely. We will certainly look at it's kind of likely. That's a really, really good question. Yeah, yeah, yeah. Good thinking on that and I don't see any other people buying mice. There we could go to the. We could go back to slides, I think. OK, Button three. Yeah. OK. Hey, Mads. Yeah, No, I do have one question for you. Feel great. Great. Alright, so you've shown extensions for structs and classes. What other types of types can I extend with extensions? So the idea is that part of the reason why? Actually, let's flip. Back. Part of the reason why we use the four keyword instead of just the colon. There's several reasons. Is that the the kinds of things you can write there is a bigger set than if you're doing inheritance or interface implementation. For instance, you could put an enum or an interface or a delegate type or or a type parameter that you just got to your generic extension that's constrained by something you know. So there really isn't a reason why we should limit ourselves to the things you can normally inherit from or to name types or whatever. So yes, we haven't really shown the power of that. I'm to be honest, I'm not sure if it works yet. Yeah, we're starting to dig into this. Yeah, but. But if you have an enum and you want to add some properties to it, you know, be our guest. Yeah, that yeah, that's why we have the syntax we chose is really, and you said it earlier, but you know, just to kind of reinforce that is that we want this to be able to scale. So not just to being able to scale to other members, right? In C# 13, we're not going to get every kind of member, right. It's it's, it's unlikely we need to get this feature out there. And so we want, we're really aiming for like methods, properties, instance and static on those. And then overtime we want to be able to say, well, maybe we could do other things. Yeah. Extension operators? Absolutely. Extension constructors? Yeah, extension, you know. Imagine the Fluent Assertions library, if you could just use equals, equals now because there's an extension operator that's being pulled in, right? There's a lot of really interesting, especially in those kind of DSL spaces where there's a really interesting things that could happen. Yeah. And a lot of really interesting challenges that we have. Tests in the lot of challenges. But hey, we're starting on a path now. As Justin said, the core scenarios, we're planning for those to be in C# 13 and maybe maybe even this indexer thing won't work. Maybe we limit it all the way down to use methods and properties. But you will tell us, OK, by, you know, by volume of voice together, what is the next important thing to do. And and just like with pattern matching and records and so on, over a couple of releases, we will use that feedback loop to to flesh the feature out and make more and more scenarios and, you know, available to you. Yeah, I mean, it's kind of like, you know, in the past we did C# releases over every like three years, right? With a new Visual Studio release way back in the day. Some of you might not even been here for those days and now it's it's still like that. It's just that you get to see it about once every 3rd of the way through that kind of kind of that that design process. Some of these features take a long time to really get them fully fleshed out. Quick one from you, Fred. What what about extension extensions? Extension extensions, That's yeah, that's another good question. We're actually thinking that to potentially disallow that, but I'm not sure. And and and instead have actual inheritance between extensions, maybe even multiple inheritance, but we are not gonna go into that obviously now and that is not going to be in C# 13. So we kind of reserving judgment on that until we've fleshed that part out. But the syntax should scale to that. So and so just to close off the last 30 seconds, you know, come meet us in the experts area. If you if you're here today, go check the resources we showed in the beginning are at these URL like they've been gathered as a resources thing for the talk. And also youknow.net nine is out now. So go download that as well. Go play with the new things and tell us what you think and help us make the release in November. Be awesome. And one last thing with that, just remember that C# 13 is not fully there yet. Thank you very much. Alright.
Info
Channel: Microsoft Developer
Views: 40,830
Rating: undefined out of 5
Keywords: .NET, Advanced (300), BRK186, Breakout, Cyrus Najmabadi, Developer tools, Dustin Campbell, English (US), Fred Silberberg, Jared Parsons, Kathleen Dollard, Mads Torgersen, Software Developer, Version v2, Visual Studio, What’s new in C# 13 | BRK186, build, build 2024, microsoft, microsoft build, microsoft build 2024, ms build, ms build 2024, msft build, msft build 2024, n2f9
Id: O3hx6oPWzX8
Channel Id: undefined
Length: 46min 26sec (2786 seconds)
Published: Mon May 27 2024
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.