1
// Protocol Buffers - Google's data interchange format
2
// Copyright 2008 Google Inc.
3
// http://code.google.com/p/protobuf/
5
// Licensed under the Apache License, Version 2.0 (the "License");
6
// you may not use this file except in compliance with the License.
7
// You may obtain a copy of the License at
9
// http://www.apache.org/licenses/LICENSE-2.0
11
// Unless required by applicable law or agreed to in writing, software
12
// distributed under the License is distributed on an "AS IS" BASIS,
13
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
// See the License for the specific language governing permissions and
15
// limitations under the License.
17
// Author: kenton@google.com (Kenton Varda)
18
// from google3/strings/substitute.h
21
#include <google/protobuf/stubs/common.h>
22
#include <google/protobuf/stubs/strutil.h>
24
#ifndef GOOGLE_PROTOBUF_STUBS_SUBSTITUTE_H_
25
#define GOOGLE_PROTOBUF_STUBS_SUBSTITUTE_H_
31
// ----------------------------------------------------------------------
32
// strings::Substitute()
33
// strings::SubstituteAndAppend()
34
// Kind of like StringPrintf, but different.
37
// string GetMessage(string first_name, string last_name, int age) {
38
// return strings::Substitute("My name is $0 $1 and I am $2 years old.",
39
// first_name, last_name, age);
42
// Differences from StringPrintf:
43
// * The format string does not identify the types of arguments.
44
// Instead, the magic of C++ deals with this for us. See below
45
// for a list of accepted types.
46
// * Substitutions in the format string are identified by a '$'
47
// followed by a digit. So, you can use arguments out-of-order and
48
// use the same argument multiple times.
49
// * It's much faster than StringPrintf.
52
// * Strings (const char*, const string&)
53
// * Note that this means you do not have to add .c_str() to all of
54
// your strings. In fact, you shouldn't; it will be slower.
55
// * int32, int64, uint32, uint64: Formatted using SimpleItoa().
56
// * float, double: Formatted using SimpleFtoa() and SimpleDtoa().
57
// * bool: Printed as "true" or "false".
59
// SubstituteAndAppend() is like Substitute() but appends the result to
63
// strings::SubstituteAndAppend(&str,
64
// "My name is $0 $1 and I am $2 years old.",
65
// first_name, last_name, age);
67
// Substitute() is significantly faster than StringPrintf(). For very
68
// large strings, it may be orders of magnitude faster.
69
// ----------------------------------------------------------------------
71
namespace internal { // Implementation details.
75
inline SubstituteArg(const char* value)
76
: text_(value), size_(strlen(text_)) {}
77
inline SubstituteArg(const string& value)
78
: text_(value.data()), size_(value.size()) {}
80
// Indicates that no argument was given.
81
inline explicit SubstituteArg()
82
: text_(NULL), size_(-1) {}
85
// We don't overload for signed and unsigned char because if people are
86
// explicitly declaring their chars as signed or unsigned then they are
87
// probably actually using them as 8-bit integers and would probably
88
// prefer an integer representation. But, we don't really know. So, we
89
// make the caller decide what to do.
90
inline SubstituteArg(char value)
91
: text_(scratch_), size_(1) { scratch_[0] = value; }
92
inline SubstituteArg(short value)
93
: text_(FastInt32ToBuffer(value, scratch_)), size_(strlen(text_)) {}
94
inline SubstituteArg(unsigned short value)
95
: text_(FastUInt32ToBuffer(value, scratch_)), size_(strlen(text_)) {}
96
inline SubstituteArg(int value)
97
: text_(FastInt32ToBuffer(value, scratch_)), size_(strlen(text_)) {}
98
inline SubstituteArg(unsigned int value)
99
: text_(FastUInt32ToBuffer(value, scratch_)), size_(strlen(text_)) {}
100
inline SubstituteArg(long value)
101
: text_(FastLongToBuffer(value, scratch_)), size_(strlen(text_)) {}
102
inline SubstituteArg(unsigned long value)
103
: text_(FastULongToBuffer(value, scratch_)), size_(strlen(text_)) {}
104
inline SubstituteArg(long long value)
105
: text_(FastInt64ToBuffer(value, scratch_)), size_(strlen(text_)) {}
106
inline SubstituteArg(unsigned long long value)
107
: text_(FastUInt64ToBuffer(value, scratch_)), size_(strlen(text_)) {}
108
inline SubstituteArg(float value)
109
: text_(FloatToBuffer(value, scratch_)), size_(strlen(text_)) {}
110
inline SubstituteArg(double value)
111
: text_(DoubleToBuffer(value, scratch_)), size_(strlen(text_)) {}
112
inline SubstituteArg(bool value)
113
: text_(value ? "true" : "false"), size_(strlen(text_)) {}
115
inline const char* data() const { return text_; }
116
inline int size() const { return size_; }
121
char scratch_[kFastToBufferSize];
124
} // namespace internal
126
LIBPROTOBUF_EXPORT string Substitute(
128
const internal::SubstituteArg& arg0 = internal::SubstituteArg(),
129
const internal::SubstituteArg& arg1 = internal::SubstituteArg(),
130
const internal::SubstituteArg& arg2 = internal::SubstituteArg(),
131
const internal::SubstituteArg& arg3 = internal::SubstituteArg(),
132
const internal::SubstituteArg& arg4 = internal::SubstituteArg(),
133
const internal::SubstituteArg& arg5 = internal::SubstituteArg(),
134
const internal::SubstituteArg& arg6 = internal::SubstituteArg(),
135
const internal::SubstituteArg& arg7 = internal::SubstituteArg(),
136
const internal::SubstituteArg& arg8 = internal::SubstituteArg(),
137
const internal::SubstituteArg& arg9 = internal::SubstituteArg());
139
LIBPROTOBUF_EXPORT void SubstituteAndAppend(
140
string* output, const char* format,
141
const internal::SubstituteArg& arg0 = internal::SubstituteArg(),
142
const internal::SubstituteArg& arg1 = internal::SubstituteArg(),
143
const internal::SubstituteArg& arg2 = internal::SubstituteArg(),
144
const internal::SubstituteArg& arg3 = internal::SubstituteArg(),
145
const internal::SubstituteArg& arg4 = internal::SubstituteArg(),
146
const internal::SubstituteArg& arg5 = internal::SubstituteArg(),
147
const internal::SubstituteArg& arg6 = internal::SubstituteArg(),
148
const internal::SubstituteArg& arg7 = internal::SubstituteArg(),
149
const internal::SubstituteArg& arg8 = internal::SubstituteArg(),
150
const internal::SubstituteArg& arg9 = internal::SubstituteArg());
152
} // namespace strings
153
} // namespace protobuf
154
} // namespace google
156
#endif // GOOGLE_PROTOBUF_STUBS_SUBSTITUTE_H_