14 Ways to Reverse a 32-Bit Integer. (And Why They Don’t Matter Anymore)

It was 2017. Pre-AI, pre-COVID. A time when people worked in places called offices, and finding a place in one meant writing cover letters, sending CVs, and having an interview with a real person.

And there I was, sitting in a small room with a department manager and two senior engineers—the three people who would decide whether I was a fit for their team.

They were well prepared. Intro. Work description. Ten technical questions—all written on a single sheet of paper. Real professionals.

Among the questions was the greatest one I have ever received:

Reverse the bit order in a 32-bit integer.

I got a pen, and my job was to write a solution. While coding on paper, I was loudly explaining what I was doing and why. I went with a simple while loop and pointers—the simpler it is, the bigger the chance the thing will compile — or would have, if writing Ctrl+F9 with my pen had any effect.

Luckily, I did not get the job. Sometimes rejection is the best thing that can happen in your life.

But the question stayed in my head. Later, I found multiple solutions—including a single ARM instruction that does exactly that. It became a fun little obsession: benchmarking different implementations and comparing them.

Now fast forward and it’s 2026. Post-COVID. Mid-AI. I am sitting on the other side, interviewing a potential candidate.

Should we ask them to do an online assessment?

The task I received ten years ago can now be solved in 30 seconds. Including all solutions I was so proud to find myself, even more. Including solid reasoning for each version. So how do you see whether the person on the other side really understands what is going on?

And if they do understand—does it even make them a good candidate? Do they need to know how to reason about code at all?

Times have changed a lot, and building teams is no longer just about whether someone is “a good fit” today. It is about predicting whether a person will still be a good fit in an environment that is going to change dramatically over the next five years. And in that context, reversing bits may not be the most valuable skill at all.

Maybe the best question nowadays is much simpler:

“Tell me about a technical question that stayed with you long after the interview was over.”

How NOT to use mocks in googletest framework and why singletons are bad

Lets make a game*. It is about marmot – a great, wild beast that can do one thing: it can sleep. Marmot’s state depends on the superposition of his universe: in the winter he sleeps. And during the night he sleeps. And if he not sleeps, he is awake. Our Universe interface will look like this:

class Universe
{
public:
    virtual ~Universe() = default;

    virtual bool IsDay() const = 0;
    virtual bool IsWinter() const = 0;
};

Now comes a brilliant idea: let’s model The Universe as a singleton class – in the end there should be only one and its state should be same for all the clients (marmots). We add this factory method.

Universe& UniverseFactory::getInstance()
{
	static RandomUniverse singleton;
	return singleton;
}

Marmot can now use it to get a Universe and figure out if he supposed to sleep or not.

MarmotState Marmot::getState() const
{
    if(UniverseFactory::getInstance().IsWinter()) {
        return MarmotState::MARMOT_IS_SLEEPING;
    }

    if(UniverseFactory::getInstance().IsDay()) {
        return MarmotState::MARMOT_IS_AWAKE;
    }

    // Oh oh - we made a mistake here! Marmot should not be awake
    return MarmotState::MARMOT_IS_AWAKE;
}

Of course everything is unit tested and all the tests are green so lets “ship it!“.

Next day the support phone line gets red hot as hundreds of people are calling, asking why their marmots are not sleeping in the middle of the night. What happened here? Why our tests did not catch this? Let’s look at them.

static UniverseMock universe;

Universe& UniverseFactory::getInstance()
{
	return universe;
}

class SomeClassTest: public ::testing::Test {
public:

	void SetUp() {}

	void TearDown() {}
};

TEST_F(MarmotTest, When_Not_Winter_And_Day_Should_Be_Awake) {
    Marmot marmot;

    EXPECT_CALL(universe, IsWinter()).WillOnce(Return(false));
    EXPECT_CALL(universe, IsDay()).WillOnce(Return(true));
    ASSERT_EQ(MarmotState::MARMOT_IS_AWAKE, marmot.getState());
}

TEST_F(MarmotTest, When_Winter_Should_Sleep) {
    Marmot marmot;

    EXPECT_CALL(universe, IsWinter()).WillRepeatedly(Return(true)); // oh!

    EXPECT_CALL(universe, IsDay()).WillOnce(Return(true));
    ASSERT_EQ(MarmotState::MARMOT_IS_SLEEPING, marmot.getState());

    EXPECT_CALL(universe, IsDay()).WillOnce(Return(false));
    ASSERT_EQ(MarmotState::MARMOT_IS_SLEEPING, marmot.getState());
}

TEST_F(MarmotTest, When_Night_Should_Sleep) {
    Marmot marmot;

    EXPECT_CALL(universe, IsDay()).WillOnce(Return(false));
    ASSERT_EQ(MarmotState::MARMOT_IS_SLEEPING, marmot.getState());
}

The last test should fail but it does not because we’ve made two terrible things: the universe mock is a static variable and there is no expectation on IsWinter in the last test. The first issue is the real problem here. The mock object does hold its state until destroyed and in the second test we asked it to always return true when ‘IsWinter’ gets called. Fine. Let’s just create and destroy the mock for every test run so the expectations don’t propagate between tests.

static UniverseMock* universe;

Universe& UniverseFactory::getInstance()
{
    return *universe;
}

class MarmotTest: public ::testing::Test {
public:

    void SetUp() {
        universe = new UniverseMock;
    }

    void TearDown() {
        delete universe;
    }
};

And this will work until one day somebody does this:

auto& universe = UniverseFactory::getInstance();

MarmotState Marmot::getState() const
{
if(universe.IsWinter()) {
return MarmotState::MARMOT_IS_SLEEPING;
}

if(universe.IsDay()) {
return MarmotState::MARMOT_IS_AWAKE;
}

...

Now we get a segfault during testing — because our singleton is recreated for each test, while the marmot updates its reference only once. Which brings us to the main conclusion of this post: singletons are bad, and we should think carefully before deciding to use them. And if we do choose to use a singleton, we need to think even harder to ensure our code remains testable.

Does that mean we have to redesign our marmot game?
Not necessarily. We can leave the bad code untouched — with the help of a magical function that verifies and clears expectations between tests. It’s called (surprise, surprise): VerifyAndClearExpectations. And we can just call it after every test run, like this:

class MarmotTest: public ::testing::Test {
public:

    void SetUp() {}

    void TearDown() {
        Mock::VerifyAndClearExpectations(&universe);
    }
};

Now tests go red and we can clearly see the root-causes – one because of wrong expectations and second because of the bug. Fix it, ship it, and go for a… not yet! First, add a “Refactor Marmot Universe” ticket to the technical backlog. Now you can go for a beer — or to sleep, if you’re a marmot and it’s winter. Or night.

*All source code can be found here