Skip to content

Commit b9ac601

Browse files
committed
not using fmt
1 parent c97c502 commit b9ac601

File tree

11 files changed

+112
-8397
lines changed

11 files changed

+112
-8397
lines changed
Lines changed: 3 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,12 @@
1-
#define CPP4R_USE_FMT
2-
#define FMT_HEADER_ONLY
3-
#include "fmt/core.h"
4-
#include "fmt/format.h"
5-
61
[[cpp4r::register]] void my_stop(std::string mystring, int myarg) {
7-
cpp4r::stop(fmt::format(fmt::runtime(mystring), myarg));
2+
cpp4r::stop(mystring);
83
}
94
[[cpp4r::register]] void my_stop_n1(std::string mystring) { cpp4r::stop(mystring); }
105
[[cpp4r::register]] void my_warning(std::string mystring, std::string myarg) {
11-
cpp4r::warning(fmt::format(fmt::runtime(mystring), myarg));
6+
cpp4r::warning(mystring);
127
}
138
[[cpp4r::register]] void my_warning_n1(std::string mystring) { cpp4r::warning(mystring); }
149
[[cpp4r::register]] void my_message(std::string mystring, std::string myarg) {
15-
cpp4r::message(fmt::format(fmt::runtime(mystring), myarg));
10+
cpp4r::message(mystring);
1611
}
1712
[[cpp4r::register]] void my_message_n1(std::string mystring) { cpp4r::message(mystring); }

extended-tests/cpp4rtest/src/test-protect.h

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,3 @@
1-
#define CPP4R_USE_FMT
2-
31
#include <testthat.h>
42

53
context("unwind_protect-C++") {
@@ -39,9 +37,7 @@ context("unwind_protect-C++") {
3937

4038
test_that("stop throws an unwind_exception") {
4139
expect_error_as(cpp4r::stop("error"), cpp4r::unwind_exception);
42-
expect_error_as(cpp4r::stop("error {}", "message"), cpp4r::unwind_exception);
43-
expect_error_as(cpp4r::stop("error {a}", fmt::arg("a", "message")),
44-
cpp4r::unwind_exception);
40+
expect_error_as(cpp4r::stop("error %s", "message"), cpp4r::unwind_exception);
4541
}
4642

4743
test_that("safe wraps R functions and works if there is an R error") {

extended-tests/cpp4rtest/tests/testthat/test_formatted_errors.R

Lines changed: 3 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,27 +1,11 @@
1-
test_that("cpp4r::stop formatting works", {
2-
test1 <- 4
1+
test_that("cpp4r::stop basic behavior", {
32
expect_error(my_stop_n1("This is a stop"), "This is a stop", fixed = TRUE)
4-
expect_error(my_stop("Your number is {}", test1), "Your number is 4", fixed = TRUE)
5-
6-
test2 <- c(3, 5, 7)
7-
expect_error(my_stop("You've tested this {} times", test2[1]), "You've tested this 3 times",
8-
fixed = TRUE)
93
})
10-
test_that("cpp4r::warning formatting works", {
11-
test1 <- "warning"
4+
test_that("cpp4r::warning basic behavior", {
125
expect_warning(my_warning_n1("This is a warning"), "This is a warning", fixed = TRUE)
13-
expect_warning(my_warning("This is a {}", test1), "This is a warning", fixed = TRUE)
14-
15-
test2 <- c("failed", "passed")
16-
expect_warning(my_warning("You {}", test2[2]), "You passed", fixed = TRUE)
176
})
18-
test_that("cpp4r::message formatting works", {
19-
test1 <- "message"
7+
test_that("cpp4r::message basic behavior", {
208
expect_message(my_message_n1("This is a message"), "This is a message", fixed = TRUE)
21-
expect_message(my_message("This is a {}", test1), "This is a message", fixed = TRUE)
22-
23-
test2 <- c("great", "super")
24-
expect_message(my_message("You're {}", test2[2]), "You're super", fixed = TRUE)
259
})
2610
test_that("cpp4r::stop works without including the fmt library", {
2711
test1 <- "error"

inst/include/cpp4r/function.hpp

Lines changed: 2 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -106,32 +106,20 @@ inline void r_message(const char* x) {
106106
} // namespace detail
107107

108108
inline void message(const char* fmt_arg) {
109-
#ifdef CPP4R_USE_FMT
110-
std::string msg = fmt::format(fmt_arg);
111-
safe[detail::r_message](msg.c_str());
112-
#else
113109
char buff[1024];
114-
int msg;
115-
msg = std::snprintf(buff, 1024, "%s", fmt_arg);
110+
int msg = std::snprintf(buff, 1024, "%s", fmt_arg);
116111
if (msg >= 0 && msg < 1024) {
117112
safe[detail::r_message](buff);
118113
}
119-
#endif
120114
}
121115

122116
template <typename... Args>
123117
void message(const char* fmt_arg, Args... args) {
124-
#ifdef CPP4R_USE_FMT
125-
std::string msg = fmt::format(fmt_arg, args...);
126-
safe[detail::r_message](msg.c_str());
127-
#else
128118
char buff[1024];
129-
int msg;
130-
msg = std::snprintf(buff, 1024, fmt_arg, args...);
119+
int msg = std::snprintf(buff, 1024, fmt_arg, args...);
131120
if (msg >= 0 && msg < 1024) {
132121
safe[detail::r_message](buff);
133122
}
134-
#endif
135123
}
136124

137125
inline void message(const std::string& fmt_arg) { message(fmt_arg.c_str()); }

inst/include/cpp4r/protect.hpp

Lines changed: 0 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -14,11 +14,6 @@
1414
#include "R_ext/Print.h" // for REprintf
1515
#include "R_ext/Utils.h" // for R_CheckUserInterrupt
1616

17-
#ifdef CPP4R_USE_FMT
18-
#define FMT_HEADER_ONLY
19-
#include "fmt/core.h"
20-
#endif
21-
2217
namespace cpp4r {
2318
class unwind_exception : public std::exception {
2419
public:
@@ -183,31 +178,6 @@ constexpr struct protect safe = {};
183178

184179
inline void check_user_interrupt() { safe[R_CheckUserInterrupt](); }
185180

186-
#ifdef CPP4R_USE_FMT
187-
template <typename... Args>
188-
void stop [[noreturn]] (const char* fmt_arg, Args&&... args) {
189-
std::string msg = fmt::format(fmt_arg, std::forward<Args>(args)...);
190-
safe.noreturn(Rf_errorcall)(R_NilValue, "%s", msg.c_str());
191-
}
192-
193-
template <typename... Args>
194-
void stop [[noreturn]] (const std::string& fmt_arg, Args&&... args) {
195-
std::string msg = fmt::format(fmt_arg, std::forward<Args>(args)...);
196-
safe.noreturn(Rf_errorcall)(R_NilValue, "%s", msg.c_str());
197-
}
198-
199-
template <typename... Args>
200-
void warning(const char* fmt_arg, Args&&... args) {
201-
std::string msg = fmt::format(fmt_arg, std::forward<Args>(args)...);
202-
safe[Rf_warningcall](R_NilValue, "%s", msg.c_str());
203-
}
204-
205-
template <typename... Args>
206-
void warning(const std::string& fmt_arg, Args&&... args) {
207-
std::string msg = fmt::format(fmt_arg, std::forward<Args>(args)...);
208-
safe[Rf_warningcall](R_NilValue, "%s", msg.c_str());
209-
}
210-
#else
211181
template <typename... Args>
212182
void stop [[noreturn]] (const char* fmt, Args... args) {
213183
safe.noreturn(Rf_errorcall)(R_NilValue, fmt, args...);
@@ -227,7 +197,6 @@ template <typename... Args>
227197
void warning(const std::string& fmt, Args... args) {
228198
safe[Rf_warningcall](R_NilValue, fmt.c_str(), args...);
229199
}
230-
#endif
231200

232201
namespace detail {
233202

inst/include/cpp4r/r_bool.hpp

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -42,10 +42,11 @@ class r_bool {
4242
private:
4343
static constexpr int na = std::numeric_limits<int>::min();
4444

45+
// C++11 constexpr must be single return statement
4546
static constexpr int from_int(int value) noexcept {
46-
if (value == static_cast<int>(FALSE)) return FALSE;
47-
if (value == static_cast<int>(na)) return na;
48-
return TRUE;
47+
return (value == static_cast<int>(FALSE)) ? FALSE :
48+
(value == static_cast<int>(na)) ? na :
49+
TRUE;
4950
}
5051

5152
int value_ = na;

inst/include/cpp4r/r_vector_writable_impl.hpp

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
#pragma once
22

33
#include "cpp4r/r_vector_fwd.hpp"
4+
#include "cpp4r/cpp_version.hpp" // for CPP4R feature detection
45

56
namespace cpp4r {
67
namespace writable {
@@ -119,6 +120,8 @@ inline r_vector<T>::r_vector(std::initializer_list<named_arg> il)
119120
// SAFETY: We've validated type and length ahead of this.
120121
const underlying_type elt = get_elt(value, 0);
121122

123+
#if CPP4R_HAS_CXX17
124+
// C++17+: Use if constexpr for compile-time dispatch
122125
if constexpr (std::is_same<T, cpp4r::r_string>::value) {
123126
// Translate to UTF-8 before assigning for string types
124127
SEXP translated_elt = Rf_mkCharCE(Rf_translateCharUTF8(elt), CE_UTF8);
@@ -137,6 +140,25 @@ inline r_vector<T>::r_vector(std::initializer_list<named_arg> il)
137140
set_elt(data_, i, elt);
138141
}
139142
}
143+
#else
144+
// C++11/14: Runtime check instead of if constexpr
145+
if (std::is_same<T, cpp4r::r_string>::value) {
146+
// Translate to UTF-8 before assigning for string types
147+
SEXP translated_elt = Rf_mkCharCE(Rf_translateCharUTF8(elt), CE_UTF8);
148+
149+
if (data_p_ != nullptr) {
150+
data_p_[i] = translated_elt;
151+
} else {
152+
set_elt(data_, i, translated_elt);
153+
}
154+
} else {
155+
if (data_p_ != nullptr) {
156+
data_p_[i] = elt;
157+
} else {
158+
set_elt(data_, i, elt);
159+
}
160+
}
161+
#endif
140162

141163
SEXP name = Rf_mkCharCE(it->name(), CE_UTF8);
142164
SET_STRING_ELT(names, i, name);

0 commit comments

Comments
 (0)