(differences)=
# Differences between C++ and Python
Many of the Nevis summer students have some previous experience with
Python, but not with C++. Here's a quick overview of the differences
to get you started. {ref}`Pay attention to the prompts `;
they tell you whether the example is in ROOT/C++ or Python.
- C++ statements end with a semi-colon. Python statements end with a
RETURN; no semi-colons.
In [] myhist.FillRandom("gaus",10000)
In [] myhist.Fit("gaus")
[] myhist.FillRandom("gaus",10000); myhist.Fit("gaus");
- Python control structures are defined by indentations. The
indentation is mandatory; ending (or increasing) the indentation is
the same as ending (or nesting) the structure. This means that when
you start working with pyroot scripts, you must be careful with the
TAB and SPACE keys. Note the colon at the end of the `for`
statement; colons are also needed at the end of `if` statements:
for jentry in xrange( entries ):
# get the next tree in the chain and verify
ientry = mychain.LoadTree( jentry )
# More stuff
print ("The loop is over")
C++ control structures (e.g., `if` statements, loops) are indicated
by curly braces ({}).[^f70] Any indentation is for the convenience of
humans; the compiler doesn't need it:
for (Int_t jentry=0; jentryC++ uses {ref}`pointers `, and ROOT makes liberal use of them in the code it
generates for you (in .C files, etc.). Python does not use pointers,
which means you don't have to remember whether to use "." or
"->":
In [] hist = ROOT.TH1D("example","my second histogram",100,-3,3)
In [] hist.FillRandom("gaus")
[] TH1* hist = new TH1D("example","my second histogram",100,-3,3);
[] hist->FillRandom("gaus");
- You have might picked up on this from the examples above: C++ has
strict rules about types, and expects you to specify them when you
create a new variable.[^f71] Python determines types dynamically, and
you rarely have to specify them:
In [] x = 2*3
In [] yae = ROOT.TH1D("test4","yet another example",200,-100,100)
[] Double_t x = 2 * 3;
[] TH1D yae = TH1D("test4","yet another example",200,-100,100);
- The ROOT C++ interpreter, cling, knows the names of all the ROOT
classes. You can type the following directly into interactive ROOT
without anything that resembles Python's `import` statement:
[] TH1D* example4 = new TH1D("example4","my fourth histogram",100,-3,3);
[] example4->Draw();
(cpp-headers)=
However, if you write a stand-alone program in
C++, you have need a `#include` for the header of any class that's not
part of the standard C++ specification:[^f72]
#include
TH1D* example4 = new TH1D("example4","my fourth histogram",100,-3,3);
example4->FillRandom("gaus",10000);
[^f70]: I'm simplifying here. All the code in this course you've have
seen so far use curly braces. I don't want to confuse you any
further (except for this footnote).
[^f71]: Since I hate to lie to you, I should remind you of the C++ `auto`
keyword, which lets C++ determine the type for you. Both of the
following are correct:
TH1D* hist = new TH1D("hist","title",100,-3,3);
auto hist = new TH1D("hist","title",100,-3,3);
This can be a great timesaver if a C++ function returns something
with a type like
`std::vector>::const_iterator`. However, you
have to be comfortable with C++ before using it, which is why I'm
relegating this C++ tip to a footnote.
How comfortable with C++ do you have to be before you can use
`auto`? Enough so that you understand why neither of the above
lines are the best choice if you're passing the pointer as an
argument to a function. A better choice might be:
auto hist = std::make_shared("hist","title",100,-3,3);
Now you know why it takes a lifetime to learn C++!
[^f72]: This is crucial if you decide to work on {ref}`Exercise 11 `.