git.iko.soy/rowtype-yoga/purescript-native
on golang help sign in
Switch to string_literal_dict (from std::map)
commit3d46983f2985eee7ab4ede5bb4fb6684530a8640 authorAndy Arvanitis <andyarvanitis@gmail.com> dateSat 1 Sep 2018, 15:44 (8 years ago) parent525b917
4 files changed+70−10
app/Main.hs+2 runtime/purescript.h+6−6 runtime/string_literal_dict.h+58 src/CodeGen/Cpp/Printer.hs+4−4
app/Main.hs+2
@@ -101,9 +101,11 @@ transpile opts jsonFile = do
101101 putStrLn implPath
102102 T.writeFile implPath $ conv (implHeader <> implementation <> implFooter)
103103 let runtime = baseOutpath </> "purescript.h"
104+ dep = baseOutpath </> "string_literal_dict.h"
104105 runtimeExists <- doesFileExist runtime
105106 when (not runtimeExists) $ do
106107 T.writeFile runtime . conv $ T.decodeUtf8 $(embedFile "runtime/purescript.h")
108+ T.writeFile dep . conv $ T.decodeUtf8 $(embedFile "runtime/string_literal_dict.h")
107109 where
108110 conv :: Text -> Text
109111 conv
runtime/purescript.h+6−6
@@ -18,9 +18,10 @@
1818#include <memory>
1919#include <functional>
2020#include <deque>
21−#include <map>
2221#include <string>
2322#include <limits>
23+#include "string_literal_dict.h"
24+
2425
2526namespace purescript {
2627
@@ -31,7 +32,7 @@ namespace purescript {
3132 public:
3233 using fn_t = std::function<boxed(const boxed&)>;
3334 using eff_fn_t = std::function<boxed(void)>;
34− using dict_t = std::map<const string, boxed>;
35+ using dict_t = string_literal_dict_t<boxed>;
3536 using array_t = std::deque<boxed>;
3637
3738 public:
@@ -107,12 +108,12 @@ namespace purescript {
107108 return f();
108109 }
109110
110− auto operator[](const string& key) const -> const boxed& {
111+ auto operator[](const char key[]) const -> const boxed& {
111112 const auto& dict = *static_cast<const dict_t*>(get());
112− return dict.at(key);
113+ return dict[key];
113114 }
114115
115− auto operator[](const string& key) -> boxed& {
116+ auto operator[](const char key[]) -> boxed& {
116117 auto& dict = *static_cast<dict_t*>(get());
117118 return dict[key];
118119 }
@@ -137,7 +138,6 @@ namespace purescript {
137138 auto& array = *static_cast<array_t*>(get());
138139 return array.at(index);
139140 }
140−
141141#endif // NDEBUG
142142
143143 }; // class boxed
runtime/string_literal_dict.hnew file+58
@@ -0,0 +1,58 @@
1+#ifndef string_literal_dict_H
2+#define string_literal_dict_H
3+
4+#include <cstring>
5+#include <string>
6+#include <vector>
7+#include <utility>
8+
9+
10+template <typename T>
11+class string_literal_dict_t : private std::vector<std::pair<const char *, T>> {
12+
13+ static auto null() -> const T& {
14+ static const T value;
15+ return value;
16+ }
17+
18+ public:
19+ using std::vector<std::pair<const char *, T>>::vector;
20+
21+ auto operator[](const char key[]) const -> const T& {
22+ for (auto it = this->cbegin(), end=this->cend(); it != end; it++) {
23+ const auto& elem_key = it->first;
24+ if (elem_key == key || !std::strcmp(elem_key, key)) {
25+ return it->second;
26+ }
27+ }
28+#ifndef NDEBUG
29+ throw std::runtime_error("dictionary key \"" + std::string(key) + "\" not found");
30+#endif
31+ return null();
32+ }
33+
34+ auto operator[](const char key[]) -> T& {
35+ const auto end = this->end();
36+ for (auto it = this->begin(); it != end; it++) {
37+ const auto& elem_key = it->first;
38+ if (elem_key == key || !std::strcmp(elem_key, key)) {
39+ return it->second;
40+ }
41+ }
42+ return this->emplace(end, key, T())->second;
43+ }
44+
45+ auto contains(const char key[]) const -> bool {
46+ for (auto it = this->cbegin(), end=this->cend(); it != end; it++) {
47+ const auto& elem_key = it->first;
48+ if (elem_key == key || !std::strcmp(elem_key, key)) {
49+ return true;
50+ }
51+ }
52+ return false;
53+ }
54+
55+};
56+
57+
58+#endif // string_literal_dict_H
src/CodeGen/Cpp/Printer.hs+4−4
@@ -199,9 +199,9 @@ literals = mkPattern' match'
199199 ]
200200 match (InstanceOf _ val ty) = mconcat <$> sequence
201201 [ return . emit $ unbox dictType val
202− , return $ emit ".count("
202+ , return $ emit ".contains("
203203 , prettyPrintCpp' ty
204− , return $ emit ") == 1"
204+ , return $ emit ")"
205205 ]
206206 match (While _ cond sts) = mconcat <$> sequence
207207 [ return $ emit "while ("
@@ -456,8 +456,8 @@ interfaceSource mn exports foreigns =
456456 identToCpp foreign' <>
457457 "() -> " <> varDecl <> " { " <>
458458 dispatchOnceBegin <>
459− foreignDict <> "().at(" <>
460− (stringLiteral . mkString $ runIdent foreign') <> "); " <>
459+ foreignDict <> "()[" <>
460+ (stringLiteral . mkString $ runIdent foreign') <> "]; " <>
461461 dispatchOnceEnd <>
462462 " };\n") <$> foreigns) <>
463463 "\n" <>