Difference between a @staticmethod and a @classmethod

@staticmethod

A @staticmethod can only be called from a class or an instance, but does not take a class or instance as its first argument.
So a @staticmethod is a helper function that is specific enough that it should belong to the class, but does not need access to the class or object.

@classmethod

A @classmethod can be called from a class or an instance and takes the class as its first argument.
You most commonly use a @classmethod to provide an alternative method of object construction (a Factory Method).

Why “using namespace std” is a bad idea

It’s not a good idea to have a statement like this in your code:

using namespace std; // or any other namespace for that matter

The problem is that when you bring in whole namespaces, there is a chance that you will bring in the same name from multiple namespaces.
If you don’t then qualify names when you use them because you don’t have to, there is a danger that they will collide.
This can mean that either:

  • The code doesn’t compile
  • Or worse, it does compile (because the function arguments and return type are coincidentally compatible), but has unpredictable results

Copy and swap idiom

The copy and swap idiom is a way of implementing the copy assignment operator in terms of the copy constructor.

  • Avoids code duplication
  • Provides a strong exception safety guarantee
  1. Create a temporary copy of the other with the copy constructor
  2. This happens implicitly because it is taken by value
  3. Swap its guts with this
  4. return *this
  5. The other is destroyed when it goes out of scope
T& T::operator=(T other)
{
    /* Swap the guts of other with this */
    return *this;
}

Creating a directory and its parents in Python

You can use the os.makedirs() function to create a new directory and any intermediate directories in its path that don’t exist:

import os
path = '/tmp/spam/eggs/ham'
os.makedirs(path)
if os.path.isdir(path):
    print 'Directory created'

The reverse operation of deleting a directory and all its subdirectories can be performed with shutil.rmtree():

import shutil
shutil.rmtree('/tmp/spam/')

Getting and setting Individual bits in a number

Set a bit

Use the bitwise OR operator (|) to set a bit (to 1).

void SetBit(unsigned char* number, unsigned int bit)
{
    *number |= 1 << bit;
}

Clear a bit

Use the bitwise AND operator (&) to clear a bit (set if to 0).
You need to invert the bit string with the bitwise NOT operator (~), then AND it.

void ClearBit(unsigned char *number, unsigned int bit)
{
    *number &= ~(1 << bit);
}

Toggle a bit

The XOR operator (^) can be used to toggle a bit.

void ToggleBit(unsigned char* number, unsigned int bit)
{
    *number ^= 1 << bit;
}

Check a bit

To check a bit, shift the number bit times to the right, then bitwise AND it.

bool CheckBit(const unsigned char *number, unsigned int bit)
{
    unsigned char temp = *number;
    return (temp >> bit) & 1;
}

Change the nth bit

The following will change the specified bit to the specified value.

void ChangeBit(unsigned char *number, unsigned int bit, bool value)
{
    *number ^= (-value ^ *number) & (1 << bit);
}

Modifying global variables in Python

You need to declare a global variable with global before you can modify it. Otherwise, you will just be creating a local variable with the same name.

x = 0

def main():
    f1(1)
    print x # prints 0
    f2(2)
    print x # prints 2

def f1(number):
    x = number

def f2(number):
    global x
    x = number

if __name__ == '__main__':
    main()

The C++ Rule of Three

The “Rule of Three” states that if you need to define one of assignment operator, copy constructor, or destructor then you probably need to define all three.
This is because defining any one implies that your class has state to manage, and if it does this needs to be considered in the other two cases.

You can prevent the managed state from being copied by making the assignment operator and copy constructor private. This makes the class non-copyable.
This can also be implemented by inheriting the class from boost::noncopyable.

If the primary purpose of your class is not resource management, you can avoid implementing any of the Rule of Three methods by wrapping the resources in classes that are designed for resource management, i.e., smart pointers like boost::shared_ptr.

Operator overloading in C++

Operators to overload

  • Assignment operator
  • Bitwise shift operators
  • Function call operator
  • Comparison operators
  • Arithmetic operators
  • Array subscripting operators
  • Pointer operators

Assignment operator

You only need to implement the assignment operator if you need to implement the copy constructor and destructor – and vice-versa.
Use the copy-and-swap idiom to implement the assignment operator:

  1. Take other by value – this invokes the copy constructor
  2. Swap the contents of this with other – you need to implement swap
  3. other is destroyed at the end of the function, taking the old state with it
X& X::operator=(X other)
{
  swap(other);
  return *this;
}

Note that this does not do a self-assignment check, but self-assignment is guaranteed to be harmless.

Bitwise shift operators

These are most commonly overloaded to insert into and extract from iostreams, or some other sort of stream.
They need to be friend functions if they need to access private members, as they can’t be members themselves.

When used with iostreams, these functions need to take the stream by non-const reference (iostreams cannot be copied and will be modified) and return it by reference.

std::ostream& operator<<(std::ostream& os, const T& obj)
{
  // Write the object to the stream
  return os;
}

std::istream& operator>>(std::istream& is, T& obj)
{
  // Read the object from the stream
  return is;
}

Function call operator

Use the function all operator to make a functor.
This is always a member function.
It can be overloaded to take any number and type of arguments.
It can return any type, or void.
Functors are often copied, so the class must be copyable and inexpensive to copy.

Comparison operators

These should be implemented as non-member functions.
Missing operators are not automatically deduced from the others.
The standard library only uses < (strict weak ordering), but you should overload them all for consistency.

You only need to fully implement operator== and operator<, as the others can be implemented in terms of them. They also make your class model the EqualityComparable and LessThanComparable concepts.

bool operator ==(const X& lhs, const X& rhs)
{
    // Do actual comparison
}
bool operator < (const X& lhs, const X& rhs)
{
    // Do actual comparison
}
bool operator !=(const X& lhs, const X& rhs)
{
    return !operator==(lhs, rhs);
}
bool operator > (const X& lhs, const X& rhs)
{
    return operator< (rhs, lhs);
}
bool operator <=(const X& lhs, const X& rhs)
{
    return !operator> (lhs, rhs);
}
bool operator >=(const X& lhs, const X& rhs)
{
    return !operator< (lhs, rhs);
}

Arithmetic operators

Unary arithmetic operators

If you overload the prefix form, you should also overload the postfix form, and vice-versa.

class X
{
    X& operator++()
    {
        // Do actual increment
        return *this;
    }

The postfix form is distinguished by a dummy int argument.
You need to use a temporary to save the old value before incrementing it so that the old value can be returned.

    X operator++(int)
    {
       X temp(*this);
       operator++();
       return temp;
    }
};

Binary arithmetic operators

You should overload op and op=.
op= is a member while op is a non-member.
You can implement op in terms of op=.
op needs to take its lhs by copy so it can modify and return it without modifying the original.

class X
{
    X& operator+=(const X& rhs)
    {
        // Do actual addition of rhs to *this
        return *this;
    }
};

X operator+(X lhs, const X& rhs)
{
    lhs += rhs;
    return lhs;
}

Array subscripting operators

These must be members. They can only take 1 argument (although it can be of any type).
You should implement const and non-const versions to allow const overloading.

class X 
{
    value_type& operator[](size_type index);
    const value_type& operator[](size_type index) const;
};

Pointer operators

This is how you implement a smart pointer.
Overload the -> and * operators.
You should implement const and non-const versions to allow const overloading.

class SmartPtr 
{
    value_type& operator*();
    const value_type& operator*() const;
    value_type* operator->();
    const value_type* operator->() const;
};

Related

Default operator== in C++