[Job Interview] C++

 

C++ STL

  • What is the time complexity of insertion in a map?

  • If you have a vector of 100 elements, and you erase elements 20 through 55, what happens to the other elements?

  • Why will you use vector instead of list, or vice versa?

  • How will you write a simple smart pointer?

  • Will auto_ptr do any reference counting before garbage collection (explicit delete)?

      This question reminds me of: How many of each type of animal did Moses bring on the Ark?
      C++ does not do garbage collection.
  • Describe a situation in which auto_ptr causes memory leak.

Object Oriented C++

  • How will you declare an abstract base class?

class Base
{
public:
    Base(){}
    virtual ~Base()=0;//pure virtual
};
 
Base::~Base()//function body required, though pure virtual
{
} 

  • What is the difference between the ideas: default constructor and implicit constructor?

default constructor:  a kind of constructor without any argument.

implicit constructor: constructors(usually including implicit default constructor and implicit copy constructor) which are generated by complier automaticly, if you lack any constructor. It is used for allocate memory, but nothing for initialization.

  • When is it important to override the implicit copy constructor provided by the compiler?

it is nearly neccessary for a defined copy constructor if a class contain one more pointer member. This will override the default behavior performed by the implicit copy constructor. For example:

class CLS
{
public:
    CLS(int i) : i_(i) { str = new char[10]; }
    ~CLS() { delete str; }
private:
    int i_;
    char * str;
};
 
int main()
{
    CLS *ptr = new CLS(1);
    CLS b(*ptr);
    delete ptr;
 
    //and here, if you access the pointer member of b, it will be a pointer pointing a destroyed memory.
    //implicit constructor just shallowly copy the members, so the above objects make their pointer member point the same memory positon!
 
    return 0;
}

  • If you override the implicit copy constructor, what other class functions should you override as well?

Also you should override the assignment operator(=).

  • What is an explicit constructor?

this is for especial use, when you wish to probide the default conversion initialization when you assign a value to a object which has a single-argument constructor. A typical case is as following:

class CLS
{
public:
    CLS(int i) : i_(i) {}
    ~CLS() {}
private:
    int i_;
};
 
int main()
{
    CLS obj = 10; 
    // ok, this will invoke the constructor, just like a type conversion.
 
    return 0;
}

for explicit keyword use:

class CLS
{
public:
    explicit CLS(int i) : i_(i) {}
    ~CLS() {}
private:
    int i_;
};
 
int main()
{
    CLS obj = 10; 
    // complier error, this time
 
    return 0;
}

  • What is a conversion constructor?

It is a concept relative to above explicit constructor. For obvious explanation, see above question.

Let p be a pointer to class B, pointing to an object of type class D, where D is derived from B. What is the dynamic type of p?

You mean:

class B
{
    //..
};
 
class D
{
    //..
};
 
B * ptr = new D;
 

 

if so, as for the pointer ptr, its static type is (B *), which is recognized by complier in complier time, while its dynamic type is (D *), it is an important feature provided by C++ called polymophism, which can be know until run time.

  • Is it possible to istantiate a class X if it has a protected constructor ?

sure, only if you provide a public static method to do the initialization works. Actually, it is the rudiment for a famous design pattern named Factory Pattern.

  • Within a derived class D, can you access a protected data member of a base class B through a pointer to D?

  • Within a derived class D, can you access a protected data member of a base class B through a pointer to B?

  • How will can you create a virtual base class without using pure virtual functions?

  • How will you implement the equivalent of a Java or ._NET interface in C++?

  • How will you force an object to perform suicide? (generally a bad idea)

It is very unsafe at least for following reason:

You probably do "delete this" in a method. After this method is called there could be at least one more method (destructor) gets called again. For example, suppose this method is called on an instance on stack, when the instance goes out of scope (end of lifetime), the destructor will be called automatically. This lead to a undefined behavor (basically depends on many things).

Why do you need it? There are situations you need this and there are many ways to handle it safely.

For more details, refer to <C++ FAQ lite>

    #include <iostream>
    using namespace std;
     
    class Base
    {
    int m_;
     
    public:
        Base(int m) : m_(m) {}
        void suicide()
        {
            cout << "Oh, suicide!" << endl;
            delete this;
        }
    };
     
    int main()
    {
        Base *ptr = new Base(1);
        ptr->suicide();
     
        Base b = Base(2);
        b.suicide();
     
        //OK, here, out of lifetime for b, the dtor invoked again!
        //this will be undefined!
     
        return 0;
    }
  • How can you write a class that ensures that its instance will be created on the heap?

      Only created on heap, an object shouldn't be create as automatic variable, but dynamicly allocated by means of new operator.

      A solution is to declare it destructor as protected( not private! why? left for you):

class HeapOnly
{
public: 
    HeapOnly() {}
    void destroy() { delete this; }
protected:
    ~HeapOnly() {}
};
 
int main()
{
    //HeapOnly a;
 
    //now out of the life time of object a, so it implicitly invokes its destructor, but it's protected!
    //so complier error: it will complain that Heap only has a private desctructor
 
    //Only correct approach:
    HeapOnly *ptr = new HeapOnly;
 
    //delete ptr; // but you cannot destroy the object by means of delete
    //Only entry to destroy by invoking a user-defined method as following:
    ptr->destroy();   
 
    return 0;
}

 

Here is another solution, which protecting the constructor, and providing a user-defined public static method instead.

class HeapOnly
{
public:
    static HeapOnly * create() { return new HeapOnly; }
    ~HeapOnly() {}
protected:
    HeapOnly() {}
};
 
int main()
{
    //HeapOnly a;
    //complier error: it invokes a protected constructor
 
    //HeapOnly * ph = new HeapOnly;
    //complier error: the same reason
 
    //Only entry for creating object, no using new and automatic variable
    HeapOnly * ptr = HeapOnly::create();
 
    //ok, using delete
    delete ptr;
 
 
    return 0;
}

 

you think what solution is more graceful? I love the later. Because the former actually has a suicide function, which results in unsafty.

  • How can you write a class that ensures that its instance will be created on the heap?

you can overload the new and delete operator and declare them protected:

class  StackOnly
{  
public:  
     StackOnly(){}  
private:  
     void* operator new(size_t);
     void operator  delete(void *ptr); 
     // 
}  
 
int main(  int  argc,  char*  argv[]  )  
{  
    StackOnly obj; //  OK  
    //StackOnly *pobj = new StackOnly;//  Error  
} 

  • Why will you declare a destructor virtual?

It's mainly for inheritant. If you don't declare the destructor virtual, thus a pointer(static type is base pointer) actually pointing the instance of its derived class will have no approach to destroy the left part but subobject, resulting in a memory leak problem. For example:

class Base
{
public:
    Base() {}
    ~Base() {}  
};
 
class Derived
{
public:
    Derived() {}
    ~Derived() { //do something }
};
 
int main()
{
    Base * ptr = new Derived;
    delete ptr;
    //problem: this just destroyed the Base subobject of the entire object, but not the part of Derived
    //because polymophism didn't occur without virtual declaration.
    
    return 0;
}

  • Can you define and invoke a pure virtual function?

Sure. At fact, it is common in the case when an abstract base class exists in a inherited hiberarchy. In that case, you should and must declare the destructor pure virtual.

For one thing, you should declare the destructor virtual because of the same reason as the above question.

For another, you also should declare at least one function pure virtual to  make the class be an abstract class.

So that is your define.

As for invoking, you can invoke it indirectly, not directly. "Indirectly" means that you cannot invoking it in your program explicitly, but by means of the pointer in run time.

Can you define and declare a static virtual function? Why?

No. The static member function has no this pointer, and this pointer is passed into every plain member function as an implicit pointer. And the virtual keyword is for polymophism which depends the pointer or reference. Therefore, you declare static virtual will be nonsense and you won't make the polymophism take effect forever.

General C++

  • What is a static type?

 

  • Does C++ use static typing or dynamic typing?

  • Is C++ strongly typed or weakly typed?

  • Does C++ perform type checking at compile time or runtime?

  • What is RTTI and what operators in C++ are available for this purpose?

  • Can your program crash before entering main()? If yes, in which situations?

  • Explain what wchar_t is used for.

  • What can the scope resolution operator be used for?

  • What is the difference between the assignment operator and the copy assignment operator?

  • What is the value of a after these two statements: a = 5; a=(a+10, a+15, 29); ?

  • In which cases is the line of code: int &i; valid or invalid?

  • Can you return a reference to public data member?

  • Can you return a reference to private data member?

  • Can you return a reference to auto object?

  • Can you return a reference to static object or data member?

  • How would you pass a 3 dimensional array of pointers by reference?

  • What is the type safe cast operator of C++ and what does it return if unsuccessful?

  • What is the difference between a dynamic_cast to a pointer and dynamic_cast to a reference?

  • Which f is being called in main?

void f(const char* x);
void f(const double x);

int main()
{
    f(0);
    return 0;
} 
  • Explain this piece of code:

try {
        throw 5;
 }
catch (int blah)
{ 
        static int myvar(blah);
}
  • How are Unexpected() and abort() related?

  • Why is it important to use a reference in catch statement?

  • How many levels of exception safety do you have in C++? (discussion question)

* Basic:  No resources leaks and no undefined behaviour due to an exception
* Strong: Same as above with "all-or-nothing" result
* No-throw: No exceptions are allowed to leave the function, and same for destructors.

Prove or disprove:

"The throw operation calls the destructors for automatic objects instantiated since 
entry to the try block."
  • Why does a copy constructor parameter need to be a const reference?

  • Which is faster: ++i or i++? Explain.

  • What are placement new, operator new, and new operator used for?

  • What is the difference between char* p, const char* p, char* const p, and const char* const p?

  • Explain what this function declaration is trying to achieve and what it ends up achieving: const int * const i_ptr func(const int* const x) const;

  • What is the difference between char a[]="string"; and char *b="string"; ?

  • How will you initialize a const data member and member references? Can this be done in multiple ways?

  • Is this code portable and standard?

#include <string>
#include <vector>
#include <cstddef>

int main()
{
    using namespace std;
    class A
    {
      vector<int>array;
      string s;
      public:
              A():array(100){}
     } a;


    unsigned char *p=reinterpret_cast<unsigned char *>(&a);
    unsigned char *v=new unsigned char[sizeof(a)];
    for(size_t i=0; i<sizeof(a); ++i)
    v[i]=p[i];
}


posted @ 2008-09-27 13:22  中土  阅读(1216)  评论(0编辑  收藏  举报
©2005-2008 Suprasoft Inc., All right reserved.