00001 #ifndef __strfmt_h__
00002 #define __strfmt_h__
00003
00004 #include "asserts.h"
00005 #include "types.h"
00006 #include "estring.h"
00007 #include "rmath.h"
00008
00009
00010
00011 template<class T>
00012 std::string size_to_string(
00013 T a_t,
00014 const std::string& a_base_size_unit = "b",
00015 uint16 a_width = 8,
00016 uint16 a_precision = 1,
00017 uint16 a_kilo = 1024
00018 )
00019 {
00020 enum {
00021 ones = 0,
00022 kilo,
00023 mega,
00024 giga,
00025 tera,
00026 peta,
00027 exa,
00028 zetta,
00029 yotta
00030 };
00031 const char* units[] = {
00032 " ",
00033 "K",
00034 "M",
00035 "G",
00036 "T",
00037 "P",
00038 "E",
00039 "Z",
00040 "Y"
00041 };
00042 std::string es;
00043 int resolution = ones;
00044 std::string str;
00045 safe_num<T> quotient = a_t;
00046 safe_num<T> remainder = 0;
00047 safe_num<T> rmul = 10;
00048 safe_num<T> tmp;
00049
00050 TRY_nomem(es = "Could not generate size-string: \"");
00051 TRY_nomem(es += estring(a_t));
00052 TRY_nomem(es += "\"");
00053
00054 for (tmp = 1; tmp < a_precision; ++tmp) {
00055 rmul *= 10;
00056 }
00057 while ((quotient >= a_kilo) && (resolution < yotta)) {
00058 TRY(
00059 tmp = quotient;
00060 tmp *= rmul;
00061
00062
00063
00064
00065
00066 remainder = (tmp / safe_num<T>(a_kilo)) % rmul;
00067 quotient /= a_kilo;
00068 ,es);
00069 resolution++;
00070 }
00071
00072 if (resolution > ones) {
00073 TRY(
00074 str += estring(quotient.value()).fmt_str(
00075 a_width-(a_precision+1)-2,estring::right,' ','x'),
00076 es);
00077 TRY_nomem(str += ".");
00078 TRY(
00079 str += estring(remainder.value()).fmt_str(a_precision,estring::right,'0','x'),
00080 es);
00081 }
00082 else {
00083 TRY(
00084 str += estring(quotient.value()).fmt_str(a_width-2,estring::right,' ','x'),
00085 es);
00086 }
00087 TRY_nomem(str += units[resolution]);
00088 TRY_nomem(str += a_base_size_unit);
00089
00090 return(str);
00091 }
00092
00093
00094
00095 template<class T>
00096 std::string num_to_string(T a_t, uint16 a_width = 0)
00097 {
00098 std::string es;
00099 std::string tstr;
00100 estring str;
00101 std::string::size_type n;
00102
00103 TRY_nomem(tstr = estring(a_t));
00104 TRY_nomem(es = "Could not generate num-string: \"");
00105 TRY_nomem(es += tstr);
00106 TRY_nomem(es += "\"");
00107
00108 if (tstr.size() == 0) {
00109 return(tstr);
00110 }
00111
00112 n = tstr.size();
00113 while (n > 0) {
00114 if (str.size() > 0) {
00115 TRY_nomem(str = "," + str);
00116 }
00117 str = tstr[(n--)-1] + str; if (n == 0) break;
00118 str = tstr[(n--)-1] + str; if (n == 0) break;
00119 str = tstr[(n--)-1] + str;
00120 }
00121
00122 if (a_width == 0) {
00123 return(str);
00124 }
00125 str.width(a_width);
00126 str.align(estring::right);
00127 TRY_nomem(tstr = str.fmt_str());
00128
00129 return(tstr);
00130 }
00131
00132
00133
00134 template<class T>
00135 std::string throughput_to_string(
00136 T a_t,
00137 const std::string& a_base_size_unit = "b",
00138 const std::string& a_base_time_unit = "s",
00139 uint16 a_width = 10,
00140 uint16 a_precision = 1,
00141 uint16 a_kilo = 1024
00142 )
00143 {
00144 std::string str;
00145
00146 TRY_nomem(
00147 str = size_to_string(a_t, a_base_size_unit, a_width-2, a_precision, a_kilo)
00148 );
00149 TRY_nomem(str += "/");
00150 TRY_nomem(str += a_base_time_unit);
00151
00152 return(str);
00153 }
00154
00155
00156 template<typename T>
00157 std::string percent_string(const T& a_complete, const T& a_total)
00158 {
00159 safe_num<double> percent;
00160 estring es;
00161 estring estr;
00162 std::string str;
00163
00164 es = "Could not calculate percentage";
00165 if (a_complete == static_cast<T>(0)) {
00166 percent = static_cast<T>(0);
00167 }
00168 else if (a_total == static_cast<T>(0)) {
00169 TRY_nomem(str = "??.?%");
00170 return(str);
00171 }
00172 else {
00173 TRY (
00174 percent = static_cast<double>(a_complete);
00175 percent *= 100;
00176 percent /= static_cast<double>(a_total);
00177 ,es);
00178 }
00179 estr.width(5);
00180 estr.align(estring::right);
00181 estr.fillchar(' ');
00182 estr.precision(1);
00183 estr = percent.value();
00184 TRY_nomem(str = estr.fmt_str());
00185 TRY_nomem(str += "%");
00186
00187 return(str);
00188 }
00189
00190 #endif