Data hiding?

Discussion in 'C++' started by Lorenzo Villari, Nov 27, 2003.

  1. I premise I don't know C++ well but... I wondered what is this data hiding
    thing... I mean, if I can look at the header (and i need it beacuse of the
    class), then what's hidden?

    Can someone give me an example of something hidden from the user?
    Lorenzo Villari, Nov 27, 2003
    #1
    1. Advertising

  2. Lorenzo Villari

    Artie Gold Guest

    Lorenzo Villari wrote:
    > I premise I don't know C++ well but... I wondered what is this data hiding
    > thing... I mean, if I can look at the header (and i need it beacuse of the
    > class), then what's hidden?
    >
    > Can someone give me an example of something hidden from the user?
    >

    Perhaps `hiding' is not the best term here.

    The idea of private class members is that code that *uses* objects
    instantiated from a class cannot access them (directly). This means
    that the class' implementation can change without needing to change
    client code.

    HTH,
    --ag

    --
    Artie Gold -- Austin, Texas
    Oh, for the good old days of regular old SPAM.
    Artie Gold, Nov 27, 2003
    #2
    1. Advertising

  3. > Perhaps `hiding' is not the best term here.
    >
    > The idea of private class members is that code that *uses* objects
    > instantiated from a class cannot access them (directly). This means
    > that the class' implementation can change without needing to change
    > client code.

    So this means I can see it but cannot use it? How useful is this?
    Oh... maybe you meant those function can be used only by a particular class?
    Is this like declaring static a function?
    Lorenzo Villari, Nov 27, 2003
    #3
  4. But wait a minute...

    Lets try an example.

    class myclass {
    private:
    int x;
    mytype y;
    public:
    myclass(...);
    };

    Notice variable 'y', it's private and users of the class can't use it so we
    say it is "hidden" or "encapsulated", but wait ... they will still have to
    define it. What if the definition of 'mytype' requires a whole bunch of
    special stuff located in a bunch of include files, the user is stuck to have
    all those definitions in his name space. Then, what if there is a change in
    one of those files, the user code won't have to be changed but it will have
    to be recompiled.

    To me this is C++ 's greatest flaw. I know there are all sorts of work
    arounds but that makes things more complicated and messy. Interesting that
    Lorenzo who "don't know C++ well " picked up on it right away.

    Perry.


    "Artie Gold" <> wrote in message
    news:...
    > Lorenzo Villari wrote:
    > > I premise I don't know C++ well but... I wondered what is this data

    hiding
    > > thing... I mean, if I can look at the header (and i need it beacuse of

    the
    > > class), then what's hidden?
    > >
    > > Can someone give me an example of something hidden from the user?
    > >

    > Perhaps `hiding' is not the best term here.
    >
    > The idea of private class members is that code that *uses* objects
    > instantiated from a class cannot access them (directly). This means
    > that the class' implementation can change without needing to change
    > client code.
    >
    > HTH,
    > --ag
    >
    > --
    > Artie Gold -- Austin, Texas
    > Oh, for the good old days of regular old SPAM.
    >
    Perry St-Germain, Nov 27, 2003
    #4
  5. Lorenzo Villari

    Artie Gold Guest

    Lorenzo Villari wrote:
    >>Perhaps `hiding' is not the best term here.
    >>
    >>The idea of private class members is that code that *uses* objects
    >>instantiated from a class cannot access them (directly). This means
    >>that the class' implementation can change without needing to change
    >>client code.

    >
    > So this means I can see it but cannot use it? How useful is this?


    Now there's an interesting question! ;-)
    Actually, a reason that private (as well as protected) members are
    `visible' (as in `you can see them in source code') is so client
    code can determine the size of an object instantiated from a class.

    > Oh... maybe you meant those function can be used only by a particular class?


    Correct. Member functions of a class -- and friends -- can use
    private members of that class; general client code cannot.

    > Is this like declaring static a function?
    >

    It's a similar concept.

    A much better explanation of all this would be found in a good book
    about C++. See http://www.accu.org for suggestions.

    HTH,
    --ag





    --
    Artie Gold -- Austin, Texas
    Oh, for the good old days of regular old SPAM.
    Artie Gold, Nov 27, 2003
    #5
  6. Lorenzo Villari wrote:
    > I premise I don't know C++ well but... I wondered what is this data hiding
    > thing... I mean, if I can look at the header (and i need it beacuse of the
    > class), then what's hidden?
    >
    > Can someone give me an example of something hidden from the user?


    The PIMPL idiom:

    http://c2.com/cgi/wiki?PimplIdiom

    The "fast pimpl" idiom:

    http://www.gotw.ca/gotw/028.htm

    and good old pure abstract classes:

    This is where there is an "interface header" file (in this case
    "library.h") - this file contains an "interface" description.
    Specifics of the implementation are undefined. Also, there exists an
    "implemnetation" file (in this case library.cpp) and this is where you
    place class descriptions that "implement" the desired behaviour, and
    finally there esists the "application" that uses the interface.

    In this scenario (for want of a better demo) I define an array interface
    "ArrayInterface" that has NO data members. The methods are virtual and
    so the application has no description of the data inside the
    implementation objects.

    In this case I implement a really nasty hack of latent copying from the
    reference WHICH IS WRONG because the assumptions are very excessive and
    easily broken.

    Anyhow - here is "data hiding" - this is used in real life even in C.

    i.e.
    // interface (library.h file)
    //
    class ArrayInterface
    {
    public:

    virtual ~ArrayInterface() {}
    virtual double & operator[]( int i ) = 0;
    };

    ArrayInterface * Factory( const char * type );

    // implementation - library.cpp file

    #include <vector>
    #include <string>

    //
    // really sick - I know - it's an array that looks
    // like doubles but is really a float - MEGGA nasty
    // hackola - demonstration purposes only, don't try
    // this at home.
    //
    class FloatArray : public ArrayInterface
    {


    std::vector<float> array;

    double temp;
    int temp_index;

    friend ArrayInterface * Factory( const char * type );

    FloatArray()
    : temp_index( -1 )
    {
    }

    void fixtemp()
    {
    if ( temp_index != -1 )
    {
    array[ temp_index ] = temp;
    temp_index = -1;
    }
    }

    double & operator[]( int i )
    {
    fixtemp();

    if ( array.size() <= i )
    {
    array.resize( i + 1 );
    }

    temp = array;
    temp_index = i;

    return temp;
    }
    };

    class DoubleArray : public ArrayInterface
    {

    friend ArrayInterface * Factory( const char * type );

    std::vector<double> array;

    double & operator[]( int i )
    {
    if ( array.size() <= i )
    {
    array.resize( i + 1 );
    }

    return array;
    }
    };



    ArrayInterface * Factory( const char * type )
    {
    if ( std::string( "float" ) == type )
    {
    return new FloatArray();
    }
    else
    {
    return new DoubleArray();
    }
    }

    #include <iostream>

    void FuncThatWorksWithArray( ArrayInterface & an_array )
    {
    std::cout << "an_array[ 30 ] = " << an_array[ 30 ] << "\n";
    std::cout << "an_array[ 20 ] = " << an_array[ 20 ] << "\n";

    }

    int main()
    {

    ArrayInterface & floater = * Factory( "float" );

    ArrayInterface & doubler = * Factory( "double" );


    floater[ 30 ] = 1.3;

    std::cout << "floater[ 30 ] = " << floater[ 30 ] << "\n";

    doubler[ 20 ] = floater[ 30 ];

    std::cout << "doubler[ 20 ] = " << doubler[ 20 ] << "\n";

    std::cout << "Doing floater\n";
    FuncThatWorksWithArray( floater );
    std::cout << "Doing doubler\n";
    FuncThatWorksWithArray( doubler );
    }
    Gianni Mariani, Nov 27, 2003
    #6
  7. Lorenzo Villari

    Cy Edmunds Guest

    "Lorenzo Villari" <> wrote in message
    news:ANcxb.149686$...
    > I premise I don't know C++ well but... I wondered what is this data hiding
    > thing... I mean, if I can look at the header (and i need it beacuse of the
    > class), then what's hidden?
    >
    > Can someone give me an example of something hidden from the user?
    >


    The point of data hiding is not to keep you from seeing it. If you're smart
    you won't look anyway. The implementation should not concern you -- only the
    interface. Any assumptions you make based on what you see in the
    implementation just make your own code less maintainable.

    If any data items in a class were not visible to the compiler, it could not
    allocate memory correctly. So we do the best we can by declaring all data in
    a class to be private to prevent the client from using the implementation
    directly. In this sense it is (sort of) "hidden".

    Google for PImpl (pointer to implementation) for a pattern related to this
    issue.

    --
    Cy
    http://home.rochester.rr.com/cyhome/
    Cy Edmunds, Nov 27, 2003
    #7
  8. Lorenzo Villari

    Jon Bell Guest

    In article <s4exb.146220$>,
    Lorenzo Villari <> wrote:
    >
    >So this means I can see it but cannot use it? How useful is this?


    You can see local variables inside an ordinary function, but you cannot
    use them directly inside other functions. How useful is this?

    :)

    --
    Jon Bell <> Presbyterian College
    Dept. of Physics and Computer Science Clinton, South Carolina USA
    Jon Bell, Nov 27, 2003
    #8

  9. > The point of data hiding is not to keep you from seeing it. If you're
    > smart you won't look anyway. The implementation should not concern you --

    only
    Please explain "If you're smart you won't look anyway"...

    > interface. Any assumptions you make based on what you see in the
    > implementation just make your own code less maintainable.

    Why?

    > If any data items in a class were not visible to the compiler, it could
    > not allocate memory correctly. So we do the best we can by declaring all

    Then is "this" pointer visible? and the compiler knows anyway you refer to a
    variable of a class... without "this" being present

    Anyway... thank you all for your answers... I'm will think about it...
    and come with new questions!
    Lorenzo Villari, Nov 27, 2003
    #9
  10. Lorenzo Villari

    Rolf Magnus Guest

    Lorenzo Villari wrote:

    >
    >> The point of data hiding is not to keep you from seeing it. If you're
    >> smart you won't look anyway. The implementation should not concern
    >> you --

    > only
    > Please explain "If you're smart you won't look anyway"...


    You're supposed to use the interface of a class and not care about how
    it's implemented at all, so you shouldn't care about private members.

    >> interface. Any assumptions you make based on what you see in the
    >> implementation just make your own code less maintainable.

    > Why?


    If the implementation changes, your code would have to change too. But
    if a class "hides" its implementation details, and you only use the
    public interface, that implementation can change without you needing to
    change the code that uses it. A simple example:

    class Foo
    {
    public:
    Foo(double lengthInCM)
    : centimeters_(lenghtInCM),
    inch_(lengthInCM * cm_to_inch)

    double centimeters() { return centimeters_; }
    double inch() { return inch_; }

    private:
    static const double cm_to_inch = 0.394;

    double centimeters_;
    double inch_;
    };

    Notice how you cannot access the member variables centimeters_ and inch_
    directly, but only through member functions. Now if the maintainer of
    that class decides that it's better to calculate the lenghts
    dynamically, he might change your class to:

    class Foo
    {
    public:
    Foo(double lengthInCM)
    : centimeters_(lenghtInCM)

    double centimeters() { return centimeters_; }
    double inch() { return centimeters_ * cm_to_inch; }

    private:
    static const double cm_to_inch = 0.394;

    double centimeters_;
    };


    Now there is no member variable inch_ anymore, but it doesn't matter,
    since the interface didn't change, and the user code will work without
    a change.

    >> If any data items in a class were not visible to the compiler, it
    >> could not allocate memory correctly. So we do the best we can by
    >> declaring all

    > Then is "this" pointer visible?


    I don't know what you mean. The "this" pointer is just a pointer to the
    current object. It only exists in non-static member function of the
    object's class.

    > and the compiler knows anyway you refer to a variable of a class...
    > without "this" being present


    Foo f;
    Foo* p = &f;

    now p points to the object f. Within member functions of class Foo, you
    can can get the same pointer under the name "this". There is no
    difference between the "this" pointer and any other pointer to the
    object.
    Rolf Magnus, Nov 27, 2003
    #10
  11. Lorenzo Villari

    Gavin Deane Guest

    "Lorenzo Villari" <> wrote in message news:<Takxb.149991$>...
    > > The point of data hiding is not to keep you from seeing it. If you're
    > > smart you won't look anyway. The implementation should not concern you --
    > > only interface.

    > Please explain "If you're smart you won't look anyway"...


    The very next sentence answers that:

    > > Any assumptions you make based on what you see in the
    > > implementation just make your own code less maintainable.

    > Why?


    Client code, ie code that _uses_ a class, should know nothing about
    how that class works internally. Otherwise, if the internals of the
    class change, the client code may no longer work. Which would be a
    maintenance problem.

    If the client code makes no assumptions about _how_ the class works,
    then the internals can change as often and as much as necessary. As
    long as the class interface stays the same, the client code will still
    work.

    This can be achieved through information hiding (making data members
    private) and through you taking no interest in how member functions
    are implemented when you use a class.

    > > If any data items in a class were not visible to the compiler, it could
    > > not allocate memory correctly. So we do the best we can by declaring all

    > Then is "this" pointer visible? and the compiler knows anyway you refer to a
    > variable of a class... without "this" being present


    I think you have two issues confused.

    The "this" pointer is only used _inside_ non-static member functions
    of a class. The code inside a member function can (and probably does)
    use private members of its class. But client code that _calls_ the
    member function should not know anything about _how_ the member
    function does its job.

    The point about the compiler allocating memoroy is this. Suppose we
    have

    // This class defintion could equally well be in a header I included.
    class foo
    {
    public:
    int bar();
    private:
    void private_helper_function();
    int private_data;
    };

    int main()
    {
    foo a_foo; // Must allocate memory for a_foo.

    // some client code that uses a_foo.
    int x = a_foo.bar();

    return 0;
    }

    To use class foo, my main function has to be able to see the class
    definition for foo, including the private section
    (private_helper_function and private_data). But my code can only
    actually use the public interface (in this case, just the member
    function "bar"). As the programmer, I do not need to look at the
    implementation of bar to be able to use the function.

    Private members of a class should not concern me when I'm using the
    class. So you could argue that having the private members included in
    the class defintion my code sees goes against information hiding.

    But when I write foo a_foo; the compiler needs to know how much memory
    to allocate for the object. The only way the compiler can know that is
    to know everything about the class, particularly what data members
    (public or private) it contains.

    It might be nice from an information hiding point of view if my code
    only needed to see the public part of the class definition. But
    without knowing that class foo has one int member and no other member
    data, the compiler would have no way of knowing how much memory to
    allocate when I write foo a_foo;

    --
    hth
    GJD
    Gavin Deane, Nov 27, 2003
    #11
  12. Lorenzo Villari

    Gary Guest

    "Perry St-Germain" <> wrote in message news:<Tqexb.21139$>...
    > But wait a minute...
    >
    > Lets try an example.
    >
    > class myclass {
    > private:
    > int x;
    > mytype y;
    > public:
    > myclass(...);
    > };
    >
    > Notice variable 'y', it's private and users of the class can't use it so we
    > say it is "hidden" or "encapsulated", but wait ... they will still have to
    > define it. What if the definition of 'mytype' requires a whole bunch of
    > special stuff located in a bunch of include files, the user is stuck to have
    > all those definitions in his name space. Then, what if there is a change in
    > one of those files, the user code won't have to be changed but it will have
    > to be recompiled.
    >
    > To me this is C++ 's greatest flaw. I know there are all sorts of work
    > arounds but that makes things more complicated and messy. Interesting that
    > Lorenzo who "don't know C++ well " picked up on it right away.


    Two things:
    1. Please note that "hidden" does not mean the same things as
    "encapsulated."

    2. Data hiding don't just mean that the user of the class cannot
    access the data directly. This misconception grows out of the way the
    language is taught with "simple" examples that don't show the whole
    story. While it is true a user can't directly access the data if the
    access is private, there is more. Suppose it is desired to encode the
    data. An account number, for example, may be changed in such a way
    that the stored data looks nothing like the account number. The
    functions that do the encoding and decoding (usually something like
    getAccout() and setAccount()) are public. The user calls the public
    interface, passing it an id and providing or getting back an account
    number. The way the account number is coded/decoded is completely
    hidden from the user since the class source code is already compiled
    and stored in an object file. If the data is written to a file (for
    example) it is encoded there.
    This is true data hiding. A second use for data hiding is to code the
    functions that set/get the data to ask for the caller's identiy and
    some proof (user id and password) and allow or disallow use of the
    data based on who is trying to use it. In other words, data hiding
    allows security measures concerning that data's use.

    Back to point 1. The keeping together of the public functions that
    manipulate the private data of the class, requiring that you have both
    parts, is the essence of encapsulation.
    --
    Gary
    Gary, Nov 28, 2003
    #12
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Brian W
    Replies:
    1
    Views:
    388
    Tian Min Huang
    Jul 18, 2003
  2. MDB
    Replies:
    3
    Views:
    505
    Natty Gur
    May 13, 2004
  3. coolwarrior
    Replies:
    2
    Views:
    2,286
    Phlip
    Aug 28, 2004
  4. Alex Hunsley

    data hiding/namespace pollution

    Alex Hunsley, Oct 31, 2005, in forum: Python
    Replies:
    12
    Views:
    585
    Steven Bethard
    Nov 1, 2005
  5. Ste
    Replies:
    41
    Views:
    785
    Thomas 'PointedEars' Lahn
    Aug 1, 2007
Loading...

Share This Page