Skip to content

Commit f802474

Browse files
committed
add std::format support to units, Temperature, and Angle
1 parent 0515c4d commit f802474

File tree

4 files changed

+50
-22
lines changed

4 files changed

+50
-22
lines changed

include/units/Angle.hpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,13 @@ template <> struct LookupName<Quantity<std::ratio<0>, std::ratio<0>, std::ratio<
2121
using Named = Angle;
2222
};
2323

24+
template <> struct std::formatter<Angle> : std::formatter<double> {
25+
auto format(const Angle& number, std::format_context& ctx) const {
26+
auto formatted_double = std::formatter<double>::format(number.internal(), ctx);
27+
return std::format_to(formatted_double, "_stRad");
28+
}
29+
};
30+
2431
inline std::ostream& operator<<(std::ostream& os, const Angle& quantity) {
2532
os << quantity.internal() << " rad";
2633
return os;

include/units/Temperature.hpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,12 @@ template <> struct LookupName<Quantity<std::ratio<0>, std::ratio<0>, std::ratio<
2121
using Named = Temperature;
2222
};
2323

24+
template <> struct std::formatter<Temperature> : std::formatter<double> {
25+
auto format(const Temperature& quantity, std::format_context& ctx) const {
26+
return std::format_to(ctx.out(), "{}_k", quantity.internal());
27+
}
28+
};
29+
2430
inline std::ostream& operator<<(std::ostream& os, const Temperature& quantity) {
2531
os << quantity.internal() << " k";
2632
return os;

include/units/units.hpp

Lines changed: 20 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -315,8 +315,9 @@ template <isQuantity Q, isQuantity R> constexpr bool operator>(const Q& lhs, con
315315
std::ratio<j>, std::ratio<n>>(static_cast<double>(value))); \
316316
} \
317317
template <> struct std::formatter<Name> : std::formatter<double> { \
318-
auto format(const Name& quantity, std::format_context& ctx) const { \
319-
return std::format_to(ctx.out(), "{}_##suffix", quantity.internal()); \
318+
auto format(const Name& number, std::format_context& ctx) const { \
319+
auto formatted_double = std::formatter<double>::format(number.internal(), ctx); \
320+
return std::format_to(formatted_double, "_" #suffix); \
320321
} \
321322
}; \
322323
inline std::ostream& operator<<(std::ostream& os, const Name& quantity) { \
@@ -610,25 +611,30 @@ template <isQuantity Q, isQuantity R> constexpr Q round(const Q& lhs, const R& r
610611

611612
// Convert an angular unit `Q` to a linear unit correctly;
612613
// mostly useful for velocities
613-
template <isQuantity Q> Quantity<typename Q::mass, typename Q::angle, typename Q::time, typename Q::current,
614-
typename Q::length, typename Q::temperature, typename Q::luminosity, typename Q::moles>
615-
toLinear(Quantity<typename Q::mass, typename Q::length, typename Q::time, typename Q::current, typename Q::angle,
616-
typename Q::temperature, typename Q::luminosity, typename Q::moles>
617-
angular,
618-
Length diameter) {
614+
template <isQuantity Q>
615+
Quantity<typename Q::mass, typename Q::angle, typename Q::time, typename Q::current, typename Q::length,
616+
typename Q::temperature, typename Q::luminosity,
617+
typename Q::moles> constexpr toLinear(Quantity<typename Q::mass, typename Q::length, typename Q::time,
618+
typename Q::current, typename Q::angle, typename Q::temperature,
619+
typename Q::luminosity, typename Q::moles>
620+
angular,
621+
Length diameter) {
619622
return unit_cast<Quantity<typename Q::mass, typename Q::angle, typename Q::time, typename Q::current,
620623
typename Q::length, typename Q::temperature, typename Q::luminosity, typename Q::moles>>(
621624
angular * (diameter / 2.0));
622625
}
623626

624627
// Convert an linear unit `Q` to a angular unit correctly;
625628
// mostly useful for velocities
626-
template <isQuantity Q> Quantity<typename Q::mass, typename Q::angle, typename Q::time, typename Q::current,
627-
typename Q::length, typename Q::temperature, typename Q::luminosity, typename Q::moles>
628-
toAngular(Quantity<typename Q::mass, typename Q::length, typename Q::time, typename Q::current, typename Q::angle,
629-
typename Q::temperature, typename Q::luminosity, typename Q::moles>
630-
linear,
631-
Length diameter) {
629+
template <isQuantity Q>
630+
Quantity<typename Q::mass, typename Q::angle, typename Q::time, typename Q::current, typename Q::length,
631+
typename Q::temperature, typename Q::luminosity,
632+
typename Q::moles> constexpr toAngular(Quantity<typename Q::mass, typename Q::length, typename Q::time,
633+
typename Q::current, typename Q::angle,
634+
typename Q::temperature, typename Q::luminosity,
635+
typename Q::moles>
636+
linear,
637+
Length diameter) {
632638
return unit_cast<Quantity<typename Q::mass, typename Q::angle, typename Q::time, typename Q::current,
633639
typename Q::length, typename Q::temperature, typename Q::luminosity, typename Q::moles>>(
634640
linear / (diameter / 2.0));

src/main.cpp

Lines changed: 17 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -6,13 +6,14 @@
66

77
constexpr int r2i(double value) { return static_cast<int>(value >= 0.0 ? value + 0.5 : value - 0.5); }
88

9-
/**
10-
* Runs initialization code. This occurs as soon as the program is started.
11-
*
12-
* All other competition modes are blocked by initialize; it is recommended
13-
* to keep execution time for this mode under a few seconds.
14-
*/
159
void initialize() {
10+
std::cout << std::format("{:.2f}", 15.2_cm) << std::endl; // should output 0.15_m
11+
std::cout << std::format("{:.2f}", 180_stDeg) << std::endl; // should output 3.14_stRad
12+
std::cout << std::format("{:.2f}", 0_celsius) << std::endl; // should output 273.15
13+
std::cout << std::format("{:.2f}", 1.2345) << std::endl;
14+
}
15+
16+
constexpr void miscTests() {
1617
units::AccelerationPose a(1_mps2, 2_mps2);
1718
Number num = Number(1.0);
1819
num = Number(0.0);
@@ -30,12 +31,18 @@ void initialize() {
3031
std::ratio<0>, std::ratio<0>, std::ratio<0>>(5.0));
3132
units::max(10_celsius, Quantity<std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>, std::ratio<0>,
3233
std::ratio<1>, std::ratio<0>, std::ratio<0>>(1.0));
34+
}
35+
36+
constexpr void v3dTests() {
3337
// check Vector3D overloads
3438
units::Vector3D<Length> v3a = 2 * units::V3Position(2_in, 2_in, 2_in) * 2;
3539
units::Vector3D<Length> v3b = units::V3Position(2_in, 2_in, 2_in) / 2.0;
3640
units::Vector3D<Area> v3c = 2_in * units::V3Position(2_in, 2_in, 2_in);
3741
units::Vector3D<Area> v3d = units::V3Position(2_in, 2_in, 2_in) * 2_in;
3842
units::Vector3D<Number> v3e = units::V3Position(2_in, 2_in, 2_in) / 2_in;
43+
}
44+
45+
constexpr void v2dTests() {
3946
// check Vector2D overloads
4047
units::Vector2D<Length> v2a = units::V2Position(2_in, 2_in) / 2;
4148
units::Vector2D<Length> v2b = 2 * units::V2Position(2_in, 2_in) * 2;
@@ -81,12 +88,14 @@ constexpr double doubleAssignmentTests() {
8188
return d;
8289
}
8390

84-
void numberOperatorTests() {
91+
constexpr void numberOperatorTests() {
8592
using namespace units_double_ops;
8693
static_assert(1_num + 2 == 3);
8794
static_assert(1 + 2_num <= 3);
8895
static_assert(1 / 2_num >= 0);
8996

9097
static_assert(numAssignmentTests() == 0);
9198
static_assert(doubleAssignmentTests() == 1);
92-
}
99+
}
100+
101+
constexpr void formatTests() {}

0 commit comments

Comments
 (0)