ROOT: An Object-Oriented Data Analysis Framework
Embedded in the ROOT system is an extensive set of GUI classes. The GUI classes provide a full OO-GUI framework as opposed to a simple wrapper around a GUI such as Motif. All GUI elements do their drawing via the TGXW low-level graphics abstract base class. Depending on the platform on which you run ROOT, the concrete graphics class (inheriting from TGXW) is either TGX11 or TGWin32. All GUI widgets are created from “first principles”, i.e., they use only routines like DrawLine, FillRectangle, CopyPixmap, etc., and therefore, the TGX11 implementation needs only the X11 and Xpm libraries. The advantage of the abstract base class approach is that porting the GUI classes to a new, non X11/Win32, platform requires only the implementation of an appropriate version of TGXW (and of TSystem for the OS interface).
All GUI classes are fully scriptable and accessible via the interpreter. This allows for fast prototyping of widget layouts.
The GUI classes are based on the XClass'95 library written by David Barth and Hector Peraza. The widgets have the well-known Windows 95 look and feel. For more information on XClass'95, see ftp://mitac11.uia.ac.be/html-test/xclass.html.
Using the ROOT Object Browser, all objects in the ROOT system can be browsed and inspected. To create a browser object, type:
root  TBrowser *b = new TBrowser
The browser, as shown in Figure 3, displays in the left pane the browse-able ROOT collections and in the right pane the objects in the selected collection. Double clicking on an object will execute a default action associated with the class of the object. Double clicking on a histogram object will draw the histogram. Double clicking on an Ntuple quantity will produce a histogram showing the distribution of the quantity by looping over all tuples in the Ntuple. Right clicking on an object will bring up a context menu (just as in a canvas).
In this section, I'll give a step-by-step method for integrating your own classes into ROOT. Once integrated, you can save instances of your class in a ROOT database, inspect objects at run-time, create and manipulate objects via the interpreter, generate HTML documentation, etc. A very simple class describing some person attributes is shown in Listing 1. The Person implementation file Person.cxx is shown in Listing 2.
The macros ClassDef and ClassImp provide some member functions that allow a class to access its interpreter dictionary information. Inheritance from the ROOT basic object, TObject, provides the interface to the database and inspection services.
Now run the rootcint program to create a dictionary, including the special I/O streamer and inspection methods for class Person:
bash$ rootcint -f dict.cxx -c Person.h
Next, compile and link the source of the class and the dictionary into a single shared library:
bash$ g++ -fPIC -I$ROOTSYS/include -c dict.cxx bash$ g++ -fPIC -I$ROOTSYS/include -c Person.cxx bash$ g++ -shared -o Person.so Person.o dict.oNow start the ROOT interactive program and see how we can create and manipulate objects of class Person using the CINT C++ interpreter:
bash$ root root  gSystem->Load("Person.so") root  Person rdm(37, 181.0) root  rdm.get_age() (int)37 root  rdm.get_height() (float)1.810000000000e+02 root  TFile db("test.root","new") root  rdm.Write("rdm") // Write is inherited from the TObject class root  db.ls() TFile** test.root TFile* test.root KEY: Person rdm;1 root  .qHere, the key statement was the command to dynamically load the shared library containing the code of your class and the class dictionary.
In the next session, we access the rdm object we just stored on the database test.root:
bash$ root root  gSystem->Load("Person.so") root  TFile db("test.root") root  rdm->get_age() (int)37 root  rdm->Dump() // Dump is inherited from the TObject class" age 37 age of person height 181 height of person fUniqueID 0 object unique identifier fBits 50331648 bit field status word root  .class Person [follows listing of full dictionary of class Person] root  .q
A C++ macro that creates and stores 1000 persons in a database is shown in Listing 3. To execute this macro, do the following:
bash$ root root  .x fill.C root  .q
This method of storing objects would be used only for several thousands of objects. The special Tree object containers should be used to store many millions of objects of the same class.
Listing 4 is a C++ macro that queries the database and prints all persons in a certain age bracket. To execute this macro, do the following:
bash$ root root  .x find.C(77,80) age = 77, height = 10077.000000 age = 78, height = 10078.000000 age = 79, height = 10079.000000 age = 80, height = 10080.000000 NULL root  find(888,895) age = 888, height = 10888.000000 age = 889, height = 10889.000000 age = 890, height = 10890.000000 age = 891, height = 10891.000000 age = 892, height = 10892.000000 age = 893, height = 10893.000000 age = 894, height = 10894.000000 age = 895, height = 10895.000000 root  .q
With Person objects stored in a Tree, this kind of analysis can be done in a single command.
Finally, a small C++ macro that prints all methods defined in class Person using the information stored in the dictionary is shown in Listing 5. To execute this macro, type:
bash$ root root  .x method.C class Person Person(int a = 0, float h = 0) int get_age() float get_height() void set_age(int a) void set_height(float h) const char* DeclFileName() int DeclFileLine() const char* ImplFileName() int ImplFileLine() Version_t Class_Version() class TClass* Class() void Dictionary() class TClass* IsA() void ShowMembers(class TMemberInspector& insp, char* parent) void Streamer(class TBuffer& b) class Person Person(class Person&) void ~Person() root  .q
The above examples prove the functionality that can be obtained when you integrate, with a few simple steps, your classes into the ROOT framework.
Getting Started with DevOps - Including New Data on IT Performance from Puppet Labs 2015 State of DevOps Report
August 27, 2015
12:00 PM CDT
DevOps represents a profound change from the way most IT departments have traditionally worked: from siloed teams and high-anxiety releases to everyone collaborating on uneventful and more frequent releases of higher-quality code. It doesn't matter how large or small an organization is, or even whether it's historically slow moving or risk averse — there are ways to adopt DevOps sanely, and get measurable results in just weeks.
Free to Linux Journal readers.Register Now!
- Three More Lessons
- Django Models and Migrations
- August 2015 Issue of Linux Journal: Programming
- Hacking a Safe with Bash
- The Controversy Behind Canonical's Intellectual Property Policy
- Secure Server Deployments in Hostile Territory, Part II
- Shashlik - a Tasty New Android Simulator
- Huge Package Overhaul for Debian and Ubuntu
- Embed Linux in Monitoring and Control Systems
- KDE Reveals Plasma Mobile