• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2014 The Android Open Source Project
2 //
3 // This software is licensed under the terms of the GNU General Public
4 // License version 2, as published by the Free Software Foundation, and
5 // may be copied, distributed, and modified under those terms.
6 //
7 // This program is distributed in the hope that it will be useful,
8 // but WITHOUT ANY WARRANTY; without even the implied warranty of
9 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10 // GNU General Public License for more details.
11 
12 #pragma once
13 
14 #include "android/base/StringView.h"
15 
16 #include <string>
17 #include <type_traits>
18 #include <utility>
19 
20 #include <stdarg.h>
21 
22 namespace android {
23 namespace base {
24 
25 // Create a new string instance that contains the printf-style formatted
26 // output from |format| and potentially any following arguments.
27 std::string StringFormatRaw(const char* format, ...);
28 
29 // A variant of StringFormat() which uses a va_list to list formatting
30 // parameters instead.
31 std::string StringFormatWithArgs(const char* format, va_list args);
32 
33 // Appends a formatted string at the end of an existing string.
34 // |string| is the target string instance, |format| the format string,
35 // followed by any formatting parameters. This is more efficient than
36 // appending the result of StringFormat(format,...) to |*string| directly.
37 void StringAppendFormatRaw(std::string* string, const char* format, ...);
38 
39 // A variant of StringAppendFormat() that takes a va_list to list
40 // formatting parameters.
41 void StringAppendFormatWithArgs(std::string* string,
42                                 const char* format,
43                                 va_list args);
44 
45 // unpackFormatArg() is a set of overloaded functions needed to unpack
46 // an argument of the formatting list to a POD value which can be passed
47 // into the sprintf()-like C function
48 
49 // Anything which can be used to construct a string goes here and unpacks into
50 // a const char*
unpackFormatArg(const std::string & str)51 inline const char* unpackFormatArg(const std::string& str) {
52     return str.c_str();
53 }
54 
55 // Forward all PODs as-is
56 template <class T>
57 constexpr T&& unpackFormatArg(T&& t,
58         typename std::enable_if<
59                     std::is_pod<typename std::decay<T>::type>::value
60                  >::type* = nullptr) {
61     return std::forward<T>(t);
62 }
63 
64 // These templated versions of StringFormat*() allow one to pass all kinds of
65 // string objects into the argument list
66 template <class... Args>
StringFormat(const char * format,Args &&...args)67 std::string StringFormat(const char* format, Args&&... args) {
68     return StringFormatRaw(format, unpackFormatArg(std::forward<Args>(args))...);
69 }
70 
71 template <class... Args>
StringAppendFormat(std::string * string,const char * format,Args &&...args)72 void StringAppendFormat(std::string* string,
73                         const char* format,
74                         Args&&... args) {
75     StringAppendFormatRaw(string, format,
76                           unpackFormatArg(std::forward<Args>(args))...);
77 }
78 
79 }  // namespace base
80 }  // namespace android
81