Oto dość zwięzły sposób, aby to zrobić:
static readonly string[] SizeSuffixes =
{ "bytes", "KB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB" };
static string SizeSuffix(Int64 value, int decimalPlaces = 1)
{
if (decimalPlaces < 0) { throw new ArgumentOutOfRangeException("decimalPlaces"); }
if (value < 0) { return "-" + SizeSuffix(-value); }
if (value == 0) { return string.Format("{0:n" + decimalPlaces + "} bytes", 0); }
// mag is 0 for bytes, 1 for KB, 2, for MB, etc.
int mag = (int)Math.Log(value, 1024);
// 1L << (mag * 10) == 2 ^ (10 * mag)
// [i.e. the number of bytes in the unit corresponding to mag]
decimal adjustedSize = (decimal)value / (1L << (mag * 10));
// make adjustment when the value is large enough that
// it would round up to 1000 or more
if (Math.Round(adjustedSize, decimalPlaces) >= 1000)
{
mag += 1;
adjustedSize /= 1024;
}
return string.Format("{0:n" + decimalPlaces + "} {1}",
adjustedSize,
SizeSuffixes[mag]);
}
A oto oryginalna implementacja, którą zasugerowałem, która może być nieznacznie wolniejsza, ale nieco łatwiejsza do naśladowania:
static readonly string[] SizeSuffixes =
{ "bytes", "KB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB" };
static string SizeSuffix(Int64 value, int decimalPlaces = 1)
{
if (value < 0) { return "-" + SizeSuffix(-value); }
int i = 0;
decimal dValue = (decimal)value;
while (Math.Round(dValue, decimalPlaces) >= 1000)
{
dValue /= 1024;
i++;
}
return string.Format("{0:n" + decimalPlaces + "} {1}", dValue, SizeSuffixes[i]);
}
Console.WriteLine(SizeSuffix(100005000L));
Należy pamiętać o jednej rzeczy - w notacji SI „kilo” zwykle używa małej litery k, podczas gdy wszystkie większe jednostki używają dużej litery. Windows używa KB, MB, GB, więc użyłem KB powyżej, ale możesz zamiast tego rozważyć kB.
if (value == 0) { return "0"; }
czek wewnątrz funkcji.Checkout ByteSize bibliotekę. To jest
System.TimeSpan
dla bajtów!Obsługuje konwersję i formatowanie za Ciebie.
Wykonuje również reprezentację ciągu i analizuje.
źródło
Ponieważ wszyscy inni publikują swoje metody, pomyślałem, że opublikuję metodę rozszerzenia, której zwykle używam do tego:
EDYCJA: dodano warianty int / long ... i naprawiono literówkę copypasta ...
źródło
Chciałbym go rozwiązać za pomocą
Extension methods
,Math.Pow
funkcji orazEnums
:i używaj go jak:
źródło
Krótka wersja najczęściej głosowanej odpowiedzi zawiera problemy z wartościami TB.
Dostosowałem go odpowiednio, aby obsługiwał również wartości tb i nadal bez pętli, a także dodałem trochę sprawdzania błędów pod kątem wartości ujemnych. Oto moje rozwiązanie:
źródło
Nie. Głównie dlatego, że jest to raczej niszowa potrzeba i istnieje zbyt wiele możliwych wariantów. (Czy to „KB”, „Kb” czy „Ko”? Czy megabajt to 1024 * 1024 bajty, czy 1024 * 1000 bajtów? - tak, w niektórych miejscach jest to używane!)
źródło
Oto opcja, która jest łatwiejsza do rozszerzenia niż twoja, ale nie, nie ma żadnej wbudowanej w samą bibliotekę.
źródło
To jest jeden ze sposobów, aby to zrobić (numer 1073741824.0 pochodzi z 1024 * 1024 * 1024 aka GB)
źródło
@ Odpowiedź Servy była miła i zwięzła. Myślę, że może być jeszcze prostsze?
źródło
Oparty na eleganckim rozwiązaniu NeverHopeless:
Może jest zbyt wiele komentarzy, ale zwykle zostawiam je, aby nie popełniać tych samych błędów podczas przyszłych wizyt ...
źródło
Nie.
Ale możesz zaimplementować w ten sposób;
Zobacz także Jak poprawnie przekonwertować rozmiar pliku w bajtach na mega lub gigabajty?
źródło
Połączyłem niektóre odpowiedzi w dwie metody, które działają świetnie. Druga metoda poniżej konwertuje z ciągu bajtów (na przykład 1,5,1 GB) z powrotem na bajty (na przykład 1621350140) jako wartość typu długiego. Mam nadzieję, że jest to przydatne dla innych, którzy szukają rozwiązania do konwersji bajtów na ciąg i z powrotem na bajty.
źródło
float.Parse
dodouble
?Wiem, że to już stary wątek. ale może ktoś będzie szukał rozwiązania. A oto czego używam i najłatwiejszy sposób
źródło
Co powiesz na:
Np. Zadzwoń jak
Spowoduje to wyjście
źródło
Poszedłem na rozwiązanie JerKimballs i kciuki za to. Chciałbym jednak dodać / wskazać, że jest to rzeczywiście kwestia kontrowersji jako całości. W swoich badaniach (z innych powodów) otrzymałem następujące informacje.
Kiedy zwykli ludzie (słyszałem, że istnieją) mówią o gigabajtach, odnoszą się do systemu metrycznego, w którym 1000 do potęgi 3 z pierwotnej liczby bajtów == liczba gigabajtów. Jednak oczywiście istnieją standardy IEC / JEDEC, które są ładnie podsumowane w Wikipedii, które zamiast 1000 do potęgi x mają 1024. Co dla fizycznych urządzeń magazynujących (i chyba logiczne, takie jak amazon i inne) oznacza stale rosnąca różnica między metrycznymi a IEC. Na przykład 1 TB == 1 terabajt metryczny to 1000 do potęgi 4, ale IEC oficjalnie określa podobną liczbę jako 1 TiB, tebibajt jako 1024 do potęgi 4. Ale, niestety, w zastosowaniach nietechnicznych (chciałbym według odbiorców) normą jest metryczna, aw mojej własnej aplikacji do użytku wewnętrznego obecnie wyjaśniam różnicę w dokumentacji. Ale do celów wyświetlania nie oferuję niczego poza metrycznymi. Wewnętrznie, mimo że nie ma to znaczenia w mojej aplikacji, przechowuję tylko bajty i wykonuję obliczenia do wyświetlenia.
Na marginesie uważam, że jest nieco nijakie, że struktura .Net AFAIK (i często się mylę, dziękuję władzom, które są), nawet w swojej wersji 4.5, nie zawiera nic na ten temat w żadnej bibliotece wewnętrznie. Można by się spodziewać, że pewnego rodzaju biblioteka open source będzie w pewnym momencie NuGettable, ale przyznaję, że jest to mały problem. Z drugiej strony System.IO.DriveInfo i inne również mają tylko bajty (tak długie), co jest raczej jasne.
źródło
źródło
A co z rekursją:
Wtedy możesz to nazwać:
źródło
Jak napisano powyżej, rekurencja jest ulubionym sposobem, przy pomocy logarytmu.
Następująca funkcja ma 3 argumenty: dane wejściowe, ograniczenie wymiaru wyniku, czyli trzeci argument.
Teraz przekonwertujmy 12 GB pamięci RAM na kilka jednostek:
źródło
Używam tego dla Windows (prefiksy binarne):
źródło
Włączyłem to (z niewielkimi modyfikacjami) do konwertera UWP DataBinding dla mojego projektu i pomyślałem, że może to być również przydatne dla innych.
Kod to:
Aby z niego skorzystać, dodaj zasób lokalny do UserControl lub Page XAML:
Odwołaj się do niego w szablonie powiązania danych lub wystąpieniu powiązania danych:
I hej presto. Dzieje się magia.
źródło
https://github.com/logary/logary/blob/master/src/Logary/DataModel.fs#L832-L837
(ZRZECZENIE SIĘ: napisałem ten kod, nawet kod w linku!)
źródło