#include <iostream>
#include <type_traits>

struct UserType{};
struct LibType1{};
struct LibType2{};

namespace def {
    struct NoOp {};

    template <typename T>
    NoOp operator ^ (T, LibType2)
    {
        static_assert(sizeof(T) == 0, "Don't do that.");
    }
}

// try commenting this out
LibType1 operator ^ (UserType, LibType2)
{
    return {};
}

void doIt(UserType ut)
{
    using namespace def;
    LibType2 lt2;
    ut ^ lt2;
}

template <typename T>
bool exists()
{
    using namespace def;
    return !std::is_same<decltype(std::declval<T>() ^ std::declval<LibType2>()), NoOp>::value;
}

int
main(void)
{
    std::cout << exists<UserType>() << std::endl;
    return 0;
}