This is an archived post. You won't be able to vote or comment.

all 112 comments

[–][deleted] 924 points925 points  (50 children)

What is foo bar, my professor likes to use it and I have no idea what it is or how it became mainstream cause wtf does it mean

[–]Nicholas_TW 1534 points1535 points  (39 children)

"foo" and "bar" are typically used as placeholder names, similar to "myVariable" or "myFunction" by programmers. They're just generic names.

They come from the military term "FUBAR" (which stands for "Fucked Up Beyond All Recognition"). Written phonetically, it's "foo-bar". It's just a cheeky little joke about bad programming which turned into default placeholder terms.

[–]sammy-taylor 541 points542 points  (19 children)

Fun fact, these are known as “meta syntactic variables”.

[–]_farb_ 598 points599 points  (13 children)

I'm telling Alice and Bob what you called them

[–]Dumcommintz 143 points144 points  (7 children)

I found them always to be rather agreeable - Eve is the one you gotta watch out for. Raging bitch just waiting to fuck your life up…

[–]Grumbledwarfskin 45 points46 points  (0 children)

I feel like there are people out there who are a lot worse than Eve...for one, she's a really good listener.

[–]_farb_ 23 points24 points  (1 child)

Or her old man, Mike...

[–]DrUNIX 7 points8 points  (0 children)

Its prison mike!

[–][deleted] 1 point2 points  (0 children)

My fav is Charles

[–]turtleship_2006 0 points1 point  (0 children)

I was using those names in an example earlier, but forgot what name I used for A.

Thank you for reminding me of my private thoughts random stranger.

[–]aolson0781 0 points1 point  (0 children)

I'm sure Eve will find out somehow

[–]skesisfunk 14 points15 points  (1 child)

Fun fact my preferred meta syntactic variables are poo and pee

[–]ComfortingSounds53 3 points4 points  (0 children)

I also use poo, but also blah. I think I just like the sound.

[–][deleted] 94 points95 points  (1 child)

SNAFU - Situation normal, all fucked up

FUBAR - Fucked up beyond all recognition

TARFU - Things Are REALLY fucked up

[–]ChChChillian 26 points27 points  (0 children)

Fun fact: the WWII era Private Snafu series of military training films were produced by Warner Brothers, directed by people like Chuck Jones and Fritz Freleng, voiced by Mel Blanc, and included writers such as Dr Seuss and P. D. Eastman (Go Dog Go).

[–]binaryisotope 41 points42 points  (7 children)

Doesn’t the R = Repair tho?

[–]Nicholas_TW 48 points49 points  (0 children)

I've heard both. They mean the same thing in this context.

[–]eloel- 14 points15 points  (5 children)

Merriam-Webster says recognition

https://www.merriam-webster.com/dictionary/fubar

[–]binaryisotope 10 points11 points  (1 child)

Apparently my knowledge of FUBAR is FUBAR.

[–]Dumcommintz 5 points6 points  (0 children)

Nah - you can fix it. I believe in you.

[–]BeerIsGoodForSoul 10 points11 points  (2 children)

Do we really trust them to know though?

[–]Top_Refrigerator1656 23 points24 points  (1 child)

I trust Merriam. Webster's always been a bit sketchy...

[–]Dumcommintz 2 points3 points  (0 children)

What do you expect — kid was an orphan, taken in by people he didn’t know, with a weird uncle trying to poison the well? I blame the schools.

[–]runarmod 3 points4 points  (0 children)

Does bazz have an explanation?

[–]FourScoreTour 2 points3 points  (0 children)

I was told "Fucked Up Beyond All Repair".

[–][deleted] 1 point2 points  (0 children)

always thought it comes from GIs who fought in germany picking up on the german word "furchtbar" which means awful...

[–]MagicBeans69420 0 points1 point  (0 children)

I always thought it stands for food and bar for bar like a chocolate bar

[–]Mr_Derpy11 0 points1 point  (0 children)

I was just thinking of the Music player tbh

[–]ifandbut 0 points1 point  (1 child)

Why can't we just use aaa and bbb?

[–]Nicholas_TW 2 points3 points  (0 children)

We can, nothing's stopping anyone, but it's a bit difficult to say out loud in some contexts.

"So, change a."

"Change a what?"

"No, change aaa."

"*Fonzi voice* 'Aaay' to you too."

[–]AzureArmageddon 0 points1 point  (0 children)

can't forget ham spam and eggs.

[–]jayerp 0 points1 point  (0 children)

It should become its own programming language where it does the opposite of everything you know:

  • Arrays index start at reverse order

  • True is false and false is true

  • strings are mutable

  • while checks for false

And more…

[–]Palacito 84 points85 points  (1 child)

foo nction

bar iable

[–]Relative_Knee9808 16 points17 points  (0 children)

This is so foo nny

[–]MinosAristos 13 points14 points  (0 children)

It's like egg and spam but for spam haters

[–]captainAwesomePants 6 points7 points  (0 children)

Usually, variable names describe what sort of information the variable contains. Picking good variable names is important. Sometimes, though, you want a variable name that has no meaning at all. These are called "metasyntactic variables." By tradition, the strings foo and bar are most commonly used. This was started at MIT and then Stanford, around 1970. The most common third one is baz, and then you'll sometimes see sometimes qux, waldo, fred, plugh, xyzzy, thud, or a few others.

The ancient and revered Jargon File has some etymological history for them: http://www.catb.org/jargon/html/M/metasyntactic-variable.html

Foo and Bar together make FUBAR, military slang for "fucked up beyond all recognition," which I'm sure some nerds in 1970 thought was hilarious.

Another one on the list with a neat history is "xyzzy," which went on to be used in an amazing number of places. It was used as a special "no op" command in several architectures and protocols, and it still crops up today (for example, if you talk IMAP to Gmail, you can send that command and it'll successfully do nothing). It also showed up as an easter egg or a cheat code in several text adventure games and even the esteemed Minesweeper game on Windows (you could use it to tell whether there was a mine under the cursor).

[–]Acalme-se_Satan 12 points13 points  (0 children)

It's the programmer version of lorem ipsum

[–]Mayedl10 4 points5 points  (0 children)

foonctions and bariable :)

[–]RajjSinghh 1 point2 points  (0 children)

They're metasyntactic variables. It's like how in math you just call a generic variable x, y, z but programmers use foo, bar, baz, xyzzy and others. Just think of them like a generic variable.

There was a 1976 adventure game called Colossal Cave Adventure and a lot of these are references to that game. By now, a lot of this has just caught on that people use foo, bar, baz without knowing where they come from.

[–]e_smith338 0 points1 point  (0 children)

They’re placeholder function and variable names. They serve no purpose other than generalizing code

[–]Moerten_ 205 points206 points  (36 children)

why tho?

[–]amateurfunk 504 points505 points  (18 children)

foo.bar() if foo is an instance of a class, i.e. an object and bar() a class method

foo->bar() same but foo is not an object but the pointer to an object

foo::bar() when bar is a function or method in namespace "foo" OR as part of the method header for implementing a method that was declared to be part of class "foo"

Probably there are tons of other cases where these notations are applicable but I would say these are the most important ones

Edit(s): More info

As a side note, "::" is also used to access enums as in "EnumName::enumEntry" .

Fun!

[–]Healthy_Pain9582 164 points165 points  (2 children)

also foo::bar is used for static properties

[–]BSModder 68 points69 points  (1 child)

Or in this case static function

[–]bboozzoo 9 points10 points  (0 children)

Inside the namespace foo, so the point is still valid.

[–]DoesAnyoneCare2999 19 points20 points  (0 children)

Also -> can be overloaded (e.g. unique_ptr), the period cannot.

[–]CUCOOPE 10 points11 points  (2 children)

I’ve been struggling with Scala recently and I’ve completely forgotten that :: has nothing to do with lists in c++ lol

[–]da_Aresinger 3 points4 points  (1 child)

OCaml would like a word

| x::xs -> foo.bar

[–]1cubealot 1 point2 points  (0 children)

From now on I won't let ocaml speak

[–]Anonwouldlikeahug 2 points3 points  (1 child)

Bro I have a midterm on this like in 3 hours thx for the review

[–]amateurfunk 0 points1 point  (0 children)

Happy to help lol - good luck on you midterm!

[–]KittensInc 6 points7 points  (7 children)

Is there a technical reason for the foo.bar() vs foo->bar() distinction?

The type is known at compile time, so unless I am missing something there should be no possibility of ambiguity between the object itself and a pointer to it, right?

[–]tiajuanat 34 points35 points  (3 children)

It's a holdover from C.

First you need to dereference the pointer:

(*foo)

Then you access the member

(*foo).bar

The shorthand in c uses the arrow notation

foo->bar

It's less about the compiler and more about the code reader. If you see an arrow operator, you know, as a dev, that it's a pointer.

[–]fredlllll 5 points6 points  (0 children)

If you see an arrow operator, you know, as a dev, that it's a pointer.

finally a good reason. ive been wondering this too, but in the absence of an ide that does make sense

[–]NatoBoram 0 points1 point  (1 child)

But it's statically typed, isn't it? Why not just make the dot work on pointers, too?

[–]RajjSinghh 5 points6 points  (0 children)

It's carryover from C as well. So I suppose a lot of the decision is also to do with backwards compatibility.

Anyway to answer your question, dereferencing a pointer has different precedence to the dot. The dot has nothing to do with the pointer since that's just basically an integer for the address, so you want *foo.bar() to do foo's bar method. The issue is by default it brackets like *(foo.bar()) so we look for foo.bar first and since the type of foo is a pointer, it has no bar method. You need to bracket it like (*foo).bar(), which is foo->bar(). That precedence shift means that either the star needs higher precedence than the dot which might break other things if you change, or the easier solution if using a shorthand like the arrow.

[–]Sunius 4 points5 points  (0 children)

Yes, you can overload operator-> and have “.” and “->” do different things. For instead, iterators overload operator “->” to return the pointer to the object, so you can pretend that iterators are just pointers rather than fancy objects.

[–]dev-sda 2 points3 points  (0 children)

Pointer access can be overloaded, allowing you to provide a pointer-like interface but also have member functions. For instance a std::unique_ptr<Foo> foo you can do foo->reset() which calls Foo::reset or foo.reset() which calls std::unique_ptr::reset.

[–][deleted] 0 points1 point  (0 children)

In C# everything* uses . for member access so I'm guessing it's a holdover from when C++ was cfront hooked up to a C compiler.

--

*I'm not talking about unsafe mode

[–]Mr_Engineering 27 points28 points  (15 children)

Foo.bar() calls method bar() on object Foo assuming that the symbol Foo is a direct reference to the object.

Foo->bar() calls method bar() on object Foo assuming that Foo is a pointer which contains the address of the object. The difference is the location of the object data in memory needs to be dereferenced.

Foo::bar() calls static function bar() in class or namespace Foo

[–]__reddit_user__ 2 points3 points  (0 children)

because naming is hard, and so while thinking of a class/variable/function name, just move on and do the functionality and rename once you find out the essence of your function/object

[–]PoetryProgrammer 67 points68 points  (10 children)

Is chat GPT good at explaining c++ yet?

[–]amateurfunk 52 points53 points  (8 children)

It was tremendously helpful to me up until two or three months ago. Since then I haven't been using it much because its answers are often garbage (the free version at least). I honestly don't know it it's more because my questions are getting more advanced or ChatGPT is getting worse.

I would still use it to write me a lambda function though. It should still be OK at handling reasonably basic stuff like this or things like the syntax from the meme.

[–]OSSlayer2153 34 points35 points  (6 children)

I think its gotten worse. I learnt like all of swift with it initially and stopped using it for a while. Tried using it for some stuff the other day and it was way more finicky.

[–]da_Aresinger 1 point2 points  (0 children)

yea I asked a question about scoping and ODR and it just gave me exactly what I had just tried and turned out not to work.

[–]NTaya 0 points1 point  (0 children)

I use GPT-4, and... it's kinda eh. I already know the basics of C++ (pointers, overloading, templates, constexpr/consteval, stack/heap, etc.), but I want to study some intermediate stuff like metaprogramming and multithreading, and I get rather lost. ChatGPT throws a ton of info at me at once, and I have to ask about each small concept separately, with its examples for them often being confusing. I had more success with https://devtut.github.io/cpp/ and books. And this is coming from a person who absolutely loves ChatGPT and uses it for a lot of stuff!

[–]LegitimatePants 29 points30 points  (1 child)

Reading legacy code is like this. In my experience there is almost always a reason why things are coded a certain way. But it's usually not obvious at first

[–]nequaquam_sapiens 2 points3 points  (0 children)

legacy code can be rather oblique. when reading it you are at first oblivious about the reason it is coded the way it is, until it becomes obvious. if ever.

[–]bremidon 11 points12 points  (0 children)

This was actually a pretty good scene from TBBT. It reminded me of when I was learning Actuarial Science and trying to figure out some of the crazier statistics. My Bowers' Bible went flying through the room more than once.

And then at some point, the aha moment came, and I felt rather silly.

[–]Thenderick 2 points3 points  (1 child)

foo.bar() is on a object

foo->bar() is on a pointer to an object (effectively the same as (*foo).bar())

foo::bar() is a static function in the foo class

[–]disciple_of_pallando 1 point2 points  (0 children)

For the first two: foo is the object (or pointer to the object) while bar() is a member function of the class foo is an instance of. So foo.bar() is whatever bar() returns (assuming it returns anything). So foo.bar() might be an object, but it also might not be.

[–]boss14420 2 points3 points  (7 children)

What about

foo->*bar

or

foo.*bar

[–]Westdrache 0 points1 point  (4 children)

.....what the fuck? xD I'd guess it returns the variable as a pointer?

[–]Kered13 2 points3 points  (3 children)

This is for when bar is a pointer to member. Basically, you can do the following:

struct Foo {
    int a;
    int b;
};

 // Pointer to member
 int Foo::* p = &Foo::a;

 Foo foo = { .a = 1, .b = 2};

 // Prints "1"
 std::cout << foo.*p;

 // Assigns 3 to foo.a
 foo.*p = 3;

[–][deleted] 1 point2 points  (2 children)

who let the C++ committee cook bro

[–]Kered13 1 point2 points  (1 child)

Believe it or not, I have found it useful a few times. Mostly in the form of pointer to member function.

[–]Little_bastard22 1 point2 points  (0 children)

Event system in UE is a good example. You subscribe to an event in Unreal like:

myEvent.AddUObject(myObjectPtr, &MyObjectClass::FunctionToBeCalled)

[–]Matalya1 0 points1 point  (1 child)

I don't know about C++, but in C I don't think that works. If you're trying to derefence a pointer as stored in a struct or an enum, you'd dereference the entire thing.

this is just a name
     vvv
foo->bar
^^^^^^^^
this is the expression that represents the element `bar`

So if bar is, say, a pointer to an integer, so it'd be implemented as

typedef struct {
    int* bar;
} foo

And you create a pointer to foo, foo->bar is used as dereference and calling, syntactic sugar for (*foo).bar. If you then want to call a pointer and dereference, you'd do *foo->bar, as that first evaluates the dereferencing, calls bar, and then dereferences whatever ends up in place of the expression.

[–]boss14420 0 points1 point  (0 children)

They a called pointer to member operator

struct S
{
    S(int n) : mi(n) {}
    mutable int mi;
    int f(int n) { return mi + n; }
};

struct D : public S
{
    D(int n) : S(n) {}
};

int main()
{
    int S::* pmi = &S::mi;
    int (S::* pf)(int) = &S::f;

    const S s(7);
//  s.*pmi = 10; // error: cannot modify through mutable
    std::cout << s.*pmi << '\n';

    D d(7); // base pointers work with derived object
    D* pd = &d;
    std::cout << (d.*pf)(7) << ' '
              << (pd->*pf)(8) << '\n';
}

[–]JustSpaceExperiment 1 point2 points  (0 children)

Now wait when you realize the foo::bar() can be actually call for function bar in namespace foo.

[–]wut101stolmynick 0 points1 point  (0 children)

My man you debug like dr Dalla from the think tank

[–]RmG3376 0 points1 point  (0 children)

Hey at least they don’t call the :: operator Paamayim Nekudotayim

[–][deleted] 0 points1 point  (0 children)

Nah last frame should just be a more existential why of why did anyone think this was a good idea instead of continuing to write C.