Every story and comment from the Hacker News API, in a layout borrowed from 2001.
A comment on Reflection for C++26. Parent comment
template<typename T> std::string to_json(const T& obj) { std::ostringstream oss; constexpr auto type_info = reflect(T); if constexpr (type_info.is_fundamental()) { // Fundamental types (int, float, etc.) if constexpr (std::is_same_v<T, bool>) { oss << (obj ? "true" : "false"); } else if constexpr (std::is_arithmetic_v<T>) { oss << obj; } else if constexpr (std::is_same_v<T, std::string>) { oss << "\"" << obj << "\""; } } else if constexpr (type_info.is_enum()) { // Enums oss << "\"" << type_info.enum_name(obj) << "\""; } else if constexpr (type_info.is_array() || std::is_same_v<T, std::vector<typename T::value_type>>) { // Arrays and vectors oss << "["; bool first = true; for (const auto& elem : obj) { if (!first) oss << ","; oss << to_json(elem); first = false; } oss << "]"; } else if constexpr (std::is_same_v<T, std::map<typename T::key_type, typename T::mapped_type>>) { // Maps oss << "{"; bool first = true; for (const auto& [key, value] : obj) { if (!first) oss << ","; oss << "\"" << key << "\":" << to_json(value); first = false; } oss << "}"; } else if constexpr (type_info.is_class()) { // Classes and structs oss << "{"; bool first = true; for (const auto& member : type_info.members()) { if (!first) oss << ","; oss << "\"" << member.name() << "\":" << to_json(member.get(obj)); first = false; } oss << "}"; } return oss.str(); } enum class Color { Red, Green, Blue }; struct Address { std::string street; std::string city; int zip; }; struct Person { std::string name; int age; double height; Color favorite_color; Address address; std::vector<std::string> hobbies; std::map<std::string, int> scores; }; int main() { Person person { "John Doe", 30, 175.5, Color::Blue, {"123 Main St", "Anytown", 12345}, {"reading", "hiking", "coding"}, {{"math", 95}, {"history", 88}, {"science", 92}} }; std::cout << to_json(person) << std::endl; return 0; }