Skip to content

Commit a03a126

Browse files
committed
draft map -> list/sexp
1 parent aeb1895 commit a03a126

File tree

3 files changed

+91
-2
lines changed

3 files changed

+91
-2
lines changed

cpp11test/DESCRIPTION

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,4 +20,4 @@ Suggests:
2020
xml2
2121
LazyData: true
2222
Roxygen: list(markdown = TRUE)
23-
RoxygenNote: 7.1.1
23+
RoxygenNote: 7.3.2

inst/include/cpp11/map_to_sexp.hpp

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
#pragma once
2+
3+
#include <map>
4+
#include <unordered_map>
5+
#include "cpp11/R.hpp"
6+
#include "cpp11/protect.hpp"
7+
#include "cpp11/list.hpp"
8+
#include "cpp11/strings.hpp"
9+
10+
namespace cpp11 {
11+
12+
template <typename Key, typename Value>
13+
SEXP map_to_sexp(const std::map<Key, Value>& map) {
14+
cpp11::writable::list result(map.size());
15+
cpp11::writable::strings names(map.size());
16+
17+
size_t i = 0;
18+
for (const auto& pair : map) {
19+
result[i] = cpp11::as_sexp(pair.second);
20+
names[i] = cpp11::as_sexp(pair.first);
21+
++i;
22+
}
23+
24+
result.names() = names;
25+
return result;
26+
}
27+
28+
template <typename Key, typename Value>
29+
SEXP unordered_map_to_sexp(const std::unordered_map<Key, Value>& map) {
30+
cpp11::writable::list result(map.size());
31+
cpp11::writable::strings names(map.size());
32+
33+
size_t i = 0;
34+
for (const auto& pair : map) {
35+
result[i] = cpp11::as_sexp(pair.second);
36+
names[i] = cpp11::as_sexp(pair.first);
37+
++i;
38+
}
39+
40+
result.names() = names;
41+
return result;
42+
}
43+
44+
} // namespace cpp11

vignettes/motivations.Rmd

Lines changed: 46 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -332,7 +332,52 @@ Doing this universally avoids many locale specific issues when dealing with Unic
332332

333333
Concretely cpp11 always uses `Rf_translateCharUTF8()` when obtaining `const char*` from `CHRSXP` objects and uses `Rf_mkCharCE(, CE_UTF8)` when creating new `CHRSXP` objects from `const char*` inputs.
334334

335-
<!--TODO: unicode examples?-->
335+
Converting R Unicode Strings to C++ Strings:
336+
337+
```cpp
338+
#include <cpp11.hpp>
339+
#include <string>
340+
341+
[[cpp11::register]]
342+
std::string convert_to_utf8(cpp11::strings input) {
343+
std::string result;
344+
for (auto str : input) {
345+
result += cpp11::r_string(Rf_translateCharUTF8(str));
346+
}
347+
return result;
348+
}
349+
```
350+
351+
```r
352+
# hello + how are you? in Japanese and Spanish
353+
input <- c("\xe3\x81\x93\xe3\x82\x93\xe3\x81\xab\xe3\x81\xa1\xe3\x81\xaf",
354+
"\xc2\xbfC\xc3\xb3mo est\xc3\xa1s\x3f")
355+
356+
convert_to_utf8(input)
357+
358+
[1] "こんにちは¿Cómo estás?"
359+
```
360+
361+
Returning Unicode Strings from C++ to R:
362+
363+
```cpp
364+
#include <cpp11.hpp>
365+
#include <string>
366+
367+
[[cpp11::register]]
368+
cpp11::writable::strings return_utf8_string() {
369+
cpp11::writable::strings result;
370+
std::string utf8_str = "こんにちは"; // Hello in Japanese
371+
result.push_back(Rf_mkCharCE(utf8_str.c_str(), CE_UTF8));
372+
return result;
373+
}
374+
```
375+
376+
```r
377+
return_utf8_string()
378+
379+
[1] "こんにちは"
380+
```
336381

337382
## C++11 features {#c11-features}
338383

0 commit comments

Comments
 (0)