You Completely Misunderstand Span in .NET | Code Cop

Поділитися
Вставка
  • Опубліковано 15 січ 2025

КОМЕНТАРІ • 112

  • @jbuchan12
    @jbuchan12 18 днів тому +24

    I wish i could find somebody who loves me as much as Nick loves a Span 😂.

  • @1vader
    @1vader 19 днів тому +117

    Please turn off automatic translation of video titles and descriptions for your videos. UA-cam apparently automatically turns it on for creators now but afaik you can turn it off somewhere in your channel settings. Translated programming terms are really confusing and it's pretry hard to figure out what the video is about from the terrible automatic German translation.

    • @crifox16
      @crifox16 19 днів тому +2

      this!!! please nick fix this if it's within your power

    • @10Totti
      @10Totti 19 днів тому +2

      you can deactivate them without any problem, for me they are very useful and I appreciate them!!!

    • @1vader
      @1vader 19 днів тому +5

      @@10Totti Only the creator can deactivate them. I'm forced to see them. And I don't understand how the title translation can possibly be useful to you? It's completely wrong and I doubt you have trouble understanding the English title if you want to watch the video. Maybe you're thinking of subtitles? That's not what I'm talking about at all.

    • @10Totti
      @10Totti 19 днів тому +1

      @@1vader I honestly see the original title despite everything, that's why maybe I didn't understand what you were saying.

    • @1vader
      @1vader 19 днів тому +4

      @@10Totti You maybe have your UA-cam language set to English. Or your language doesn't have title translations yet. Changing the language to English just means I'll get translated titles for German videos which I also don't want.

  • @MrTwiddler0
    @MrTwiddler0 14 днів тому +2

    I think the main point that the tip was trying to convey (albeit poorly executed) was to suggest writing functions that don't rely on string types and use spans instead. The ability to create high performance code is possible if it's able to avoid requiring a string. The over reliance on the string data type in the dotnet ecosystem is something that applications are still paying a performance penalty for still. My wish is that one day soon choosing between string or span offers the same API level support across all frameworks.

  • @MZZenyl
    @MZZenyl 19 днів тому +31

    Good message, mad example.
    Console.WriteLine does indeed not have an overload for ReadOnlySpan, but Console.Out.WriteLine does. Console.Out points to a TextWriter for the console, which has a lot of overloads.
    Similarly, Console.WriteLine(StringBuilder) resolves to Console.WriteLine(Object), which just calls .ToString() on the StringBuilder, resulting in a string allocation. But Console.Out.WriteLine(StringBuilder) is a specific overload that iterates over the segments of the StringBuilder, thereby avoiding string allocation.

  • @izhovkin
    @izhovkin 19 днів тому +54

    While Console.WriteLine does not have Span overload (yet?), Console.Out.WriteLine has, and it indeed will save some memory allocations if using spans.
    So, at least in case where you end up writing text to some sort of stream (network or file) spans can be considered.

    • @davidmartensson273
      @davidmartensson273 19 днів тому +3

      Same I assume if your going to write the span to any stream and do not really need the string part.
      As for using span, I have started to use it more and more but carefully so that I do not fall into traps and also so I do not end up making code I have a hard time reading and maintaining.
      Most of the code I write is not performance critical and readability is far more important, but "free" gains where I do not have to sacrifice readability is good :)

    • @ErazerPT
      @ErazerPT 19 днів тому +4

      @@davidmartensson273 It all comes down to "how further down the line do i need that .ToString() ?". If the answer is never, then instantly going to Span or some sort of array makes every bit of sense. If it's "on the next line", then it makes no sense at all. Everything else falls in between.
      As for the readability, totally agree, and add "headaches" to that. In some other langs/systems where you have String and byte[] being intermixed and used around in a quasi random way, you find yourself sticking to byte[] only because "at least it's predictable"...

  • @henningerhenningstone691
    @henningerhenningstone691 16 днів тому +2

    Span is sort of like async/await in how it spreads itself across the codebase once you start using it. Everything that can have a ReadOnlySpan overload instead of taking string, eventually will. Since strings are immutable anyway, there should rarely be a reason to create new string objects instead of working with the strings you already have, unless you're actually creating a completely new string, but that would then only be done via some form of StringBuilder (keep in mind that literals are compiled in, while interpolation also uses StringBuilder)

  • @I-PixALbI4-I
    @I-PixALbI4-I 19 днів тому +10

    We need 2/24 hours course about Spans and where to use it and where not to use )

  • @Robert-yw5ms
    @Robert-yw5ms 19 днів тому +13

    I'd like to congratulate myself on seeing the flaw in the comparison despite literally only knowing Spans from these videos.

  • @vbachris
    @vbachris 19 днів тому +4

    the people who are concerned about the computational efficiency difference between Span and Substring are also the people who put Web API calls in their unit tests.

  • @Cafe-O-Milk
    @Cafe-O-Milk 8 днів тому

    is always a welcomed video. Any underused and underrated topic really :D

  • @GuidoSmeets385
    @GuidoSmeets385 19 днів тому +61

    I don't really worry all that much about these kind of optimizations. As long as we have sql queries that can be improved from 2sec to 100ms any and all micro optimizations on the webserver are meaningless.

    • @akaHarvesteR
      @akaHarvesteR 19 днів тому +7

      This is the way.

    • @michaelsutherland5848
      @michaelsutherland5848 19 днів тому +8

      The vast majority of the time, you're right. Nick's professional focus is very much on scalable systems, and that's where microseconds and bytes start to count. Most developers only have to get that deep to resolve performance bottlenecks in a very targeted fashion.

    • @dfbdtrhgwtwd7149
      @dfbdtrhgwtwd7149 19 днів тому +3

      If your website has 5 users per day, or if you only ever process 5 data records, then you'd be correct! It's all a matter of scale (of the person's mind).

    • @w32crazydev
      @w32crazydev 19 днів тому +2

      unless you re dealing with 10 million users. a Span optimization there can literally save infrastructure costs up to 20k/month. believe me

    • @vbachris
      @vbachris 19 днів тому +2

      the people who are concerned about the computational efficiency difference between Span and Substring are also the people who put Web API calls in their unit tests.

  • @SG_01
    @SG_01 19 днів тому +5

    The project I'm on for work has a dated system originally written in c++ that communicates between servers by just casting data to structures. I had to add a new server, but needed it to be in c#. Luckily you can do similar things in c#, and you end up using span / readonlyspan to deal with inline arrays and strings in the packets.
    And I would say the original advice makes sense if you are going to process the span further rather than getting the string.

  • @rauberhotzenplotz7722
    @rauberhotzenplotz7722 19 днів тому +23

    Correct me if i'm wrong, but another difference is, that with Substring the original string can be garbage collected, with AsSpan it cannot.

    • @ethanr0x
      @ethanr0x 19 днів тому +1

      great point

    • @SG_01
      @SG_01 19 днів тому +2

      Yes, but it depends if say a calling function still has a reference to the string or something like that. ReadOnlySpan can not exists on the heap anyway, so the lifetime will likely be similar in the end

    • @ethanr0x
      @ethanr0x 19 днів тому

      @@SG_01 it depends if the string is a field in an object and if not, then whether the calling function uses the string after the call. The AsSpan just creates another root for the string to prevent GC

    • @anantmishra6783
      @anantmishra6783 19 днів тому

      it's kind of a given, don't you think? Since it's on the stack...

    • @MrWuffels
      @MrWuffels 19 днів тому +6

      Span doesn't have to be garbage collected. It's lifetime will end when it's out of scope and the stackframe it's living on ends

  • @mattbristo6933
    @mattbristo6933 9 днів тому

    I haven't used Span much but interested to learn more.

  • @oleksii766
    @oleksii766 8 днів тому

    Agree. Just returning span is the same as just returning reference. It doesn't make sense without a particular context.

  • @JasonKaler
    @JasonKaler 19 днів тому +5

    Span and that whole family are great if you don't need strings. The problem is that most things usually need strings.
    It would be great if they made string equivalents for spans and for UTF8 so that you didn't actually need strings.
    It irks me that your API gets sent UTF8, converted to strings, manipulated as strings and then converted back to UTF8 in the response.
    It blew me away how much more efficient systems become when they keep everything in 1 format.

    • @TomasHruska01
      @TomasHruska01 18 днів тому

      JsonSerializer has an overload that takes a span of bytes. So you can read messages received over the internet into an array rented from ArrayPool, then pass them as spans to the deserializer, and get rid of the biggest offenders when it comes to memory allocations.

  • @RandallEike
    @RandallEike 19 днів тому +2

    Microsoft takes care to optimize core functions, so it is a relatively safe bet that "Substring" and other methods that provide specific functionality are going to be faster (and safer) than your one line home grown alternative. It's no surprise that string.AsSpan().ToString is more than twice as slow as string.Substring().

  • @10Totti
    @10Totti 19 днів тому +1

    Thanks for audio track translate!

  • @luisf7
    @luisf7 19 днів тому +7

    The LinkedIn post was great, though. As a byte representation of text, Span and string are pretty much the same for use cases where you only need to read data and not store it. Just because .NET tooling doesn't have as much support for Span as string, that doesn't invalidate that Span is very often just as capable as string for doing what one needs. And more often than not, people default to use substring for being used to it. Maybe you could say that the post didn't really go into the differences between the two in detail, but I don't think a LinkedIn post is the place to explain into that much detail, and he did explain superifically the differences

  • @foamtoaster9742
    @foamtoaster9742 19 днів тому +3

    MORE SPANS pls Nick, love this content

    • @vbachris
      @vbachris 19 днів тому +1

      span span span span, wonderful span, glorous span

  • @dotnetMasterCSharp
    @dotnetMasterCSharp 19 днів тому

    most useful for big data, thank you

  • @fredrikjosefsson3373
    @fredrikjosefsson3373 17 днів тому +1

    Something I'd like to see in a video is some explanation about IEnumerable. For instance should an endpoint in an API return an IEnumerable, or a List/Collection/Array
    Also some of the differences using array, collection, hashset, list would be interesting to learn more about. I personally just go by preference, If I'm not going to add more data I will use a readonly collection instead of a list, but I am not sure what the difference between a collection and an array is so sometimes I use array instead with no reason why I choose that instead of a collection

  • @kapilgupta4409
    @kapilgupta4409 5 днів тому

    Very well explained/ Span is a hype nothing more it seems !

  • @kenbrady119
    @kenbrady119 14 днів тому

    Span span span span span span span. Oops, I was thinking of Monty Python. Happy New Year coders!
    And yes, I've just started trying to utilize span, so please give us more.

  • @KingOfBlades27
    @KingOfBlades27 19 днів тому

    Amazing LinkedIn content as usual 😂

  • @Azcane
    @Azcane 19 днів тому +23

    I kind of disagree here.
    In many, if not most cases, I'm using span to get part of a string, I'm doing some parsing or simple comparisons after and don't need a "real string" at all. In these cases, there definitely is the proclaimed benefit because no string is created. Saying that one will need the string eventually is really not true in my experience.
    IMHO, the main message should be "delay string creations as much as you can, using Span, because mostly you don't even need a string". And neither the poster of the message nor you really got that point across.
    Edit: Your video makes it seem like there's no point in using span like this because it'll be created anyways, just at a later point, which I really doubt was your intention.

    • @nickchapsas
      @nickchapsas  19 днів тому +12

      Did you actually listen to the conclusion in the end?

    • @Azcane
      @Azcane 19 днів тому +7

      @@nickchapsas Yes, I've watched your whole video but I fail to see how that makes my comment invalid.
      My whole point is that in many cases a new string representing a substring just isn't needed and a Span would be an actual replacement and not "meaningless" or "fake".
      As long as the library support is there (and it's pretty good by now), a Span is an actual equal replacement to "a real string" in my opinion.
      Also, "If spans were that good we wouldn't have strings anymore" is just so besides the point. Of course a string is something different than a span. But talking about a substring, which already is allocated in memory inside another string, a span absolutely is an equal replacement to another new string.

    • @visose0
      @visose0 19 днів тому +6

      ​@@Azcane Like Nick mentions, it's like comparing an IEnumerable that hasn't been processed yet to populating a List and claiming that it's much faster and you will never use a List again. Sure, you can argue that sometimes you might only need the first value of the IEnumerable so in this case it's more appropriate, but without clarifying critical information, the statement is misleading at best and very reasonable to assume that the original author doesn't understand the difference.

  • @mDoThis
    @mDoThis 18 днів тому

    When I've seen the title of this video my first thought was "uh oh, someone's triggered Nick and there's high probability of shouting in this video" :D

  • @zumalifeguard3493
    @zumalifeguard3493 19 днів тому +6

    Nick, I think you're slightly off on this one from the philosophical point of view. If Span was there from the beginning, .NET 1.0, APIs wouldn't take string as a parameter, but take Span. Your comment about "you eventually have to convert it to a string, otherwise we'd be using Span everywhere", sounds like you're saying the reason we don't use Span everywhere, but string is used is for some good design reason. It's not. The correct response would have been, "Unfortunately Span cannot be used in every case where it could have been used because of legacy, which means you will often need to convert it to string anyway".
    I would still stick with using Span as a default, and convert to String as late as possible because you may not need to convert it at all.
    Of course the other reason to convert to string is to retain a fully copy of it as the original string may no longer be available.

    • @omoton802
      @omoton802 18 днів тому +3

      But Nick is criticising the point of the original post about using Span instead of Substring based on whats available today. The original post is misrepresenting the performance improvement in that case as Substring is obviously returning a string.

  • @GameDevNerd
    @GameDevNerd 13 днів тому

    I've got a scary little adventure for ya to try ... you want a sub-string out the original string and want to be cool and use a span, but still need a string for Console.WriteLine ... so get the pointer to your span and underyling string, then new() a string up using the pointer, offset and length! 😈

  • @SirBenJamin_
    @SirBenJamin_ 19 днів тому

    I've added the fact that I use spans to my CV.

  • @anantmishra6783
    @anantmishra6783 19 днів тому +9

    try this pls in the benchmark instead of the .Tostring() in UseSpanString:
    public String Substr(string input)
    {
    return string.Create(input.Length, input, (chars, state) =>
    {
    state.AsSpan(10,5).CopyTo(chars);
    });
    }

    • @brandon-22
      @brandon-22 19 днів тому +8

      well anantmishra don't keep us in suspense, you wrote the code, share the stats!

    • @anantmishra6783
      @anantmishra6783 19 днів тому

      @@brandon-22Here are the stats
      | Method | Mean | Error | StdDev | Median | Allocated |
      |-------------- |----------:|----------:|----------:|----------:|----------:|
      | UseSubstring | 3.8485 ns | 0.0530 ns | 0.0470 ns | 3.8278 ns | 32 B |
      | UseSpan | 0.0000 ns | 0.0002 ns | 0.0001 ns | 0.0000 ns | - |
      | UseSpanstring | 2.8395 ns | 0.0236 ns | 0.0197 ns | 2.8317 ns | 32 B |
      | UseSpanString | 7.4686 ns | 0.1497 ns | 0.1401 ns | 7.4134 ns | 32 B |
      | SpanString | 4.1984 ns | 0.0298 ns | 0.0249 ns | 4.1919 ns | 32 B |
      //Added Code
      public string SpanString() => string.Create(5, TestString, (chars, state) => { state.AsSpan(10, 5).CopyTo(chars); });

    • @anantmishra6783
      @anantmishra6783 19 днів тому +1

      @@brandon-22 Unfortunately my comment is getting deleted when I post the benchmark scores, bottom line is this, string.create is 0.2ns slower than substring and 3ns faster than UseSpanString() which uses .toString() to create string from span. Just makes sense to use substring in a scenario where you may want a string from a span.
      but yes, the premise that using span when you need to create a string anyways is incorrect, as the penalty to create a string from span is negligible, using the string.create method... ;)

    • @phizc
      @phizc 19 днів тому +1

      ​@@anantmishra6783but in your code, the span is only used inside the String.Create lambda. It would be more interesting to see the perf if the creation of the span happens before and then passed to String.Create. Otherwise it's just a slower and more cumbersome way of using .Substring.

  • @tempusmagia486
    @tempusmagia486 19 днів тому

    We need another span hate video, abusing it is also bad and since this channel already convinced a lot to use spans, they got the wrong message of "use span always" and seeing that in my codebase where it doesn't belong is kinda frustrating.

  • @lodevijk
    @lodevijk 17 днів тому

    Why are we talking about micro optimization, just use whatever readable code you need.
    You might as well just write your code in IL and be proud it's so efficient

  • @dmitrykim3096
    @dmitrykim3096 19 днів тому

    People need to understand hiw the memory works and what is underneath the operations to trully optimze the code

  • @matteobarbieri2989
    @matteobarbieri2989 18 днів тому

    This is where the law stops and I start😂

  • @qorxmazmaharram8300
    @qorxmazmaharram8300 13 днів тому

    Guys, Span explanation completely wrong. Span is just struct and allocation itself happens on stack but not underlying data structures! There is misunderstanding when span is used for iterate massive array or some string in that case so much candidate explain that why span is fast they say because span allocates on stack not heap for this array iteration is so fast. It's partially true but not because when span iterate it's just accessing underlying array directly from the in memory as unsafe code that's is it. But I understand why they explain like that because of I stated above it's allocation happens stack and massive array also allocate on stack but it's totally wrong for this its lead to misunderstanding span work

  • @codefoxtrot
    @codefoxtrot 19 днів тому +2

    It's never my instinct to use a Span. Could use a video that shows opportunities where Span should be considered, so maybe I can trick myself into at least recognizing, after the fact. Thanks. Linked-in is horrible.

    • @andyfitz1992
      @andyfitz1992 19 днів тому

      Typically, the slice method extracts the section of memory containing the values, which you can then perform decision based logic over. Loops are also faster using span/immutable-arrays. Generally, I've only ever used it where speed is needed and I know 'exactly' the format of the data I am dealing with on a method that will get called 100k times+

  • @sanampakuwal
    @sanampakuwal 19 днів тому

    Please Span these Spans videos, Nick!

  • @smathlax
    @smathlax 19 днів тому +1

    If you need to process your text use a span to avoid needless memory allocation; if not keep it as a string.
    Just as if you need to add/remove elements to your collection, use a list to avoid needless memory allocation; if not keep it as an array.
    Just because a concept supercedes or is more complex than another concept, doesn't mean we should never use the bog-standard old concept.

  • @oussama7132
    @oussama7132 19 днів тому

    the linkedin post seems ai generated, or i can't tell the difference anymore

  • @Bankoru
    @Bankoru 18 днів тому

    Yeah Span strings are always great until you remember you need to turn them back to strings.

  • @alexanderkvenvolden4067
    @alexanderkvenvolden4067 19 днів тому

    You know, converting to an IEnumerable is always a lot faster than ToArray.........

  • @ErazerPT
    @ErazerPT 19 днів тому +1

    Dear god, this was making me so mad before you even went further... Author is either dumb or disingenuous. It's apples to oranges obviously. Had he qualified it with "if you only need something akin to a read only byte[]", sure, makes sense NOT to use SubString, but if you don't, you're just telling it to create a ref object to a memory region AND THEN telling it to alloc and copy that memory to a string object. Double the work for no gain. And this is the issue with people not ever having done low level work. Anyone that ever wrote C or similar would instantly write this off as "from the stupid bin", but because people either won't think or won't know about the low level work being done and treat it as "magic", this passes as a "good idea".

  • @neverlandhomie
    @neverlandhomie 19 днів тому

    Hey Nick, I'm missing an important point here! What's really missing here is the topic of unicode. String can deal with that, chars can't.
    By the way, I use Span, primarily to process binary data, e.g. from the network stack, and “cast” it into structs using MemoryMarshaller.

    • @jupahe6448
      @jupahe6448 18 днів тому

      strings in c# are UTF-16 thus chars are essentially ushorts meaning they do support unicode up to 0xFFFF
      after that you will need to use 2 chars, string or not,
      the only place where it's dealt with is the text rendering engine or console and in the string LITERALS in your source code, neither have anything to do with the string object at runtime
      correct me if I'm wrong but in terms of unicode there is no difference between using a string or a Span

  • @M3lodicDeathmetal
    @M3lodicDeathmetal 6 днів тому

    I don't agree with this video and I also find the benchmarking falls short. This is such a short example (a 5character substring) that it doesn't really matter what you do. Obviously, use the right tool for the right job, but you make it sound like Span is almost never the right tool.

  • @goodoleme747
    @goodoleme747 7 днів тому

    I'm confused...I remember you putting a video out doing a similar thing comparing span's to Substring. ua-cam.com/video/FM5dpxJMULY/v-deo.html

  • @franciscovilches6839
    @franciscovilches6839 17 днів тому

    Ha! Nick also explaining .ToString() & Span 3 years ago when introducing span. ua-cam.com/video/FM5dpxJMULY/v-deo.htmlsi=UyaU_-0LDAzFX-jW&t=747

  • @calvinwilson3617
    @calvinwilson3617 19 днів тому +3

    Airpods or scissors? Comment below

    • @vinitrech
      @vinitrech 19 днів тому +9

      scissors definitely, seems much more performant

    • @xRealHackerx
      @xRealHackerx 19 днів тому +5

      Scissors can give you a much deeper feeling, but that's only once per ear.

    • @phizc
      @phizc 19 днів тому

      Both is cutting cords.

  • @ErikBongers
    @ErikBongers 18 днів тому

    "Comparing apples to oranges" is the wrong expression. It's misleading.
    It's like saying you can't compare the speed of a car to a bike because they are 2 different things.
    Unfortunately, in simplified examples, you may create a test that causes confusion. To stay with the analogy, if you test both vehicles by driving around the block you could argue that you need to include the parking time, thus the bike wins! But the parking time is just an artifact of the test and isn't meant to be included.
    Same with the WriteLine. It's part of the test setup and not of the actual test.
    In Nick's defense, in a real situation you have to look at the whole use case.
    On a side note, does Console.Out.WriteLine prevent the creation of an intermediate string? Would the whole test setup be faster with that function?

  • @dfbdtrhgwtwd7149
    @dfbdtrhgwtwd7149 19 днів тому +2

    Poor explanation, @Nick Chapsas. What you should have explained is that a Span is not a new object allocated on the Heap, but a ref struct, pointing to the original string, allocated in the Stack Frame. Spans are best used in the methods, which accept Span-typed parameters, not for conversion back to strings. That's what really matters.

    • @nickchapsas
      @nickchapsas  19 днів тому +1

      I have explained this in detail years ago. I don’t need to explain what span is every time I talk about span

    • @dfbdtrhgwtwd7149
      @dfbdtrhgwtwd7149 19 днів тому +2

      @@nickchapsas I think you do - that's what your channel is for... Isn't it? :)

  • @rafazieba9982
    @rafazieba9982 19 днів тому

    I think Nick is way to harsh criticizing this post. The only thing to take from all this is that AsSpan(...).ToString() is way slower than Substring(...). I wonder why that is.

  • @topiquewot
    @topiquewot 19 днів тому

    Content in this video is for programming kids man. Maybe something more advanced and useful.

  • @MatinDevs
    @MatinDevs 18 днів тому

    Blazor is dying, then our dude is talking about spoons

  • @01110100011101110110
    @01110100011101110110 19 днів тому +5

    Unsubscribed. Maybe if you stop using clickbait titles, I will consider subscribing again.

    • @nickchapsas
      @nickchapsas  19 днів тому +5

      It’s literally what I said to the author of the post. No idea what you’re talking about mate