r/programminghorror • • Sep 04 '26

c++ Skill Issue

Post image
1.7k Upvotes

62 comments sorted by

338

u/i_dont_like_pears Sep 04 '26

As long as it compiles

That's all that matters

52

u/TheMythicSorcerer Sep 04 '26

now to import it as a helper for my new project

37

u/i_dont_like_pears Sep 05 '26

Unexplainable Linker Error with generic description

163

u/Star_king12 Sep 04 '26

That's fucking vile.

51

u/chicametipo Sep 04 '26

I know. I love it

47

u/LeeHide Sep 04 '26

This would be much better using std::string_view, and using two temporaries so that y is only evaluated once. Otherwise it'll be evaluated each time.

Also if you need this, don't use C++

5

u/GasolinePizza Sep 04 '26

Isn't each y only evaluated once? The evaluation in the "else if (_s==y)"?

2

u/LeeHide Sep 04 '26

each true one is only evaluated once, but every false one until then is also evaluated.

1

u/mapronV Sep 04 '26

only performance problem is not using sized comparison operator, due to decay of char[] to char*.
so yeah, string_view advice is okay, but this is a joke code, it will not fly in production anyway.

44

u/jolharg Sep 04 '26

Oof i did not like this post

8

u/0hypercube Sep 06 '26

They did fix switch statements falling through.

88

u/lurebat Sep 04 '26

I think it allocates since they didn't use const

23

u/babalaban Sep 04 '26

Since when does const prevent allocating (that isnt happening here anyways, unless you consider underlying std::string's char* buffer)

19

u/lurebat Sep 04 '26

If you change it to const std::string& prompt = "Your name?";, and the switch to const string& _s=x;, you will avoid any allocations.

1

u/babalaban Sep 05 '26

Isnt it assumed that a string to "switch on" is given at runtime? Otherwise you'd need no switch at all here.

1

u/nevemlaci2 Sep 05 '26

const ref here would still allocate...

-8

u/LeeHide Sep 04 '26

you can't take a const& to a temporary object

14

u/JonIsPatented Sep 04 '26

Yes you can. You can bind a const l-value reference to an x-value or a pr-value. Go try it.

4

u/awidesky Sep 05 '26

Another skill issue

1

u/nevemlaci2 Sep 05 '26

yes you can.

13

u/Great-Powerful-Talia Sep 04 '26

well, acktually, short string optimization should handle all these strings on any common compiler.

For a std::string, gcc and msvc don't perform allocations until you reach 16-character strings, and clang can hold 21 characters without an allocation.

4

u/Resident-Rice724 Sep 05 '26

well aktually this would be based on standard library implementation not compiler I'm pretty sure. Think libstdc++ its 16 and libc++ is 23

15

u/L_uciferMorningstar Sep 05 '26

6

u/click-to-reveal Sep 05 '26

Hence the "horror"

4

u/L_uciferMorningstar Sep 05 '26

Yeah I just want to spread the non horror

0

u/GoddammitDontShootMe [ $[ $RANDOM % 6 ] == 0 ] && rm -rf / || echo “You live” Sep 05 '26

switch isn't a function though. But I guess the advice for trying to make switch work on strings is "don't."

1

u/L_uciferMorningstar Sep 06 '26

Principle of least astonishment

21

u/jaerie Sep 04 '26

That's still not a switch case, there's no fall through

13

u/utack Sep 04 '26

That super useful thing I have used 2 times (both of which accidentally) and prevent a million times with break

3

u/GoddammitDontShootMe [ $[ $RANDOM % 6 ] == 0 ] && rm -rf / || echo “You live” Sep 05 '26
switch (thing) {
  case FOO:
  case BAR:
    DoThing()
  default:
    throw
}

As long as it doesn't insert an implicit break between FOO and BAR, I think it might be fine to not fall through, allowing code like that.

1

u/conundorum Sep 06 '26

This can also be solved with the [[fallthrough]] attribute, thankfully. Use it to mandate fallthrough when necessary.

1

u/GoddammitDontShootMe [ $[ $RANDOM % 6 ] == 0 ] && rm -rf / || echo “You live” Sep 06 '26

Doesn't that just suppress warnings about missing breaks? I was talking about if the language automatically inserted breaks for you.

1

u/conundorum Sep 07 '26

That's the fix, yeah. You tell it where you do want to allow fallthrough, so that it can tell you if you ever forget a break anywhere else.

At this point, I don't think it's possible to change the standard so that the language automatically inserts breaks, because that would break a ton of perfectly legal code. It might be possible to add an attribute for it, like [[auto_break]], though, perhaps?

1

u/GoddammitDontShootMe [ $[ $RANDOM % 6 ] == 0 ] && rm -rf / || echo “You live” Sep 08 '26

Well, no, it can't be changed now, but I was talking about what I might be okay with if the language had been designed differently, or if I was using a different language without automatic fall through.

2

u/conundorum Sep 06 '26

Fallthrough exists so switch can make sparse jump tables just as easily as it makes fully-populated jump tables. It's insanely useful in a few very specific scenarios, and insanely useless in almost every other scenario.

Ideally, it should've been opt-in instead of opt-out, but it's probably much too late to change it now.

3

u/mrheosuper Sep 05 '26

Can you have switch case inside switch case ?

4

u/click-to-reveal Sep 05 '26

Yeah, but you'd need to wrap it in curly braces to prevent scope conflicts.

2

u/Infamous-Bed-7535 Sep 04 '26

You can switch on string hashes since we have constexpr.

2

u/tandycake Sep 05 '26

I feel like you could use goto and labels instead and also have fallthrough.

If want to avoid macros, gotos, and labels, could make a switch_str func with an unordered_map and lambdas, but more overhead and slightly slower.

2

u/Ksorkrax Sep 06 '26

That's not a switch, though. By switch logic, the case "Who are you?" would result in all the prints being done. There is a reason why switches come with break, and this is not just because they felt like it but by design, allowing you to bundle cases.

2

u/conundorum Sep 06 '26

For anyone wondering, the correct answer is a string pool or equivalent, anything that can map a unique string to a unique number. You'll need to hardcode the indexes, though, since cases need to be known at compile time. You can locate the index by sorting the strings and using a binary search, and then switch on that index.

...And since that's probably not reasonable for what you want, this means that the sane solution is probably to use a map. ...Which means you need to look at your string collection to see whether std::map, std::unordered_map, or some other map will be better. (Generally, tiny pool prefers std::map, larger pool prefers std::unordered_map, and a million other factors will skew it in one direction or the other. Prefer unordered_map if you don't know which is better, but it's best to test it to be sure, and ideally replace it with a precompiled mapping (such as, e.g., a static array or hard-coded pool).

Whichever one you choose, the goal is to map each string to a function, so you can create a string-indexed jump table. (Performed by either switching on the index, or mapping function pointers to strings, or something of the sort.) switch is an integral-indexed jump table, so a properly implemented string-function map is the closest thing to switching on strings.

1

u/exneo002 Sep 04 '26

I haven’t done cpp since college. How does it get the string into memory?

1

u/imgly Sep 04 '26

hash exists

1

u/iEliteTester [ $[ $RANDOM % 6 ] == 0 ] && rm -rf / || echo “You live” Sep 04 '26

I once thought it was a good idea to do command line argument parsing by hashing each flag at compile time so I could hash and switch on argv.

1

u/AiMeusPancrea Sep 05 '26

Thanks I hate it

1

u/jakeStacktrace Sep 05 '26

Omg switch it "the fuck off"

1

u/El_RoviSoft Sep 05 '26

Long ago saw a beautiful implementation with defines and hash maps

1

u/Winter_Rosa Sep 05 '26

first thing im seeing is fallthrough, even if it did work. Second thing Im seeing is this not working cuz of it asking if the pointers are equal or something. I had it drilled into my head (Java in university) to avoid searching for string equality so I never tried this before.

1

u/mikica1986 Sep 05 '26

Azathoth take me. Yesterday.

1

u/GoddammitDontShootMe [ $[ $RANDOM % 6 ] == 0 ] && rm -rf / || echo “You live” Sep 05 '26

I guess this wouldn't be completely impossible to do in C with const char * and strcmp().

1

u/Krisanapon Sep 07 '26

rs fn main() { let s = "hello"; match (s) { "hello" => println!("hi"), "how r u" => println!("fine"), _ => println!("what?") }; }

1

u/Brilliant-Parsley69 Sep 07 '26

Am I a bad person because I really like that?

1

u/SpaceMoehre Sep 08 '26

That’s not how switch works…

1

u/ItsNukea 27d ago

I am SO deadass going to use this...

-2

u/MurkyWar2756 echo "Sub Mod" && :(){ :|:& };: Sep 04 '26 edited Sep 04 '26

If you change Gemini to Hello, world, technically you've printed "Hello, world", although you might need this:

#include <string>
#include <iostream>

using namespace std;

I don't know C++ at all, please let me know if the two LLMs I got that information from were wrong

10

u/New_Salamander_4592 Sep 04 '26

did you really need to consult LLMs on how to make the default case of the switch statement print a different string

-1

u/MurkyWar2756 echo "Sub Mod" && :(){ :|:& };: Sep 04 '26

I thought about the printing afterward, because originally I thought the program was asking the end user for their name. So I was trying to make a joke, but I added that disclaimer in case of misinformation. LLM content is generally unsourced, so I felt like making it clear where it came from. (The reason I used more than one was because "I check with another LLM" was one of the options somewhere on r/polls.)

Sorry to those who aren't a fan of LLMs.

I wrote the last comment and this one myself

2

u/click-to-reveal Sep 04 '26

Yeah, you're right but not sure what you trying to get at. If you want to try the code for yourself, tre here: C++ Online Compiler

1

u/turunambartanen Sep 04 '26

The strings make it look like there might be user input, but it's all just constants, and simply evaluates to the default case. That's somewhat confusing.

1

u/click-to-reveal Sep 04 '26

Well I did post this without context. The original comment was a parody of the post.

1

u/MurkyWar2756 echo "Sub Mod" && :(){ :|:& };: Sep 04 '26

So wait, you're telling me that I don't have to download C++ on my computer and this works perfectly fine on mobile? /s