fork download
  1. struct B64 {
  2. table: Vec<char>,
  3. }
  4. impl B64 {
  5. fn new() -> B64 {
  6. B64{table: "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/".chars().collect()}
  7. }
  8. fn _push(bs: &mut Vec<bool>, byte: u8, width: i32) {
  9. for i in 0..width {bs.push(byte >> (width - 1 - i) & 1 != 0);}
  10. }
  11. fn encode(&self, s: &str) -> String {
  12. let mut bs: Vec<bool> = Vec::new();
  13. for b in s.as_bytes() {B64::_push(&mut bs, *b, 8)}
  14. for _ in 0..6 - bs.len() % 6 {bs.push(false)}
  15. let mut cs: Vec<char> = bs.chunks(6)
  16. .map(|b6| b6.iter().enumerate().fold(0, |acc, (i, b)| acc + ((*b as u8) << (5 - i))))
  17. .map(|u| self.table[u as usize]).collect();
  18. for _ in 0..4 - cs.len() % 4 {cs.push('=')}
  19. cs.into_iter().collect()
  20. }
  21. fn decode(&self, s: &str) -> String {
  22. let mut bs: Vec<bool> = Vec::new();
  23. for c in s.chars().take_while(|d| *d != '=') {
  24. if let Some(i) = self.table.iter().position(|e| *e == c) {B64::_push(&mut bs, i as u8, 6)}
  25. }
  26. let newlen = bs.len() - bs.len() % 8;
  27. bs.truncate(newlen);
  28. let us: Vec<u8> = bs.chunks(8)
  29. .map(|b8| b8.iter().enumerate().fold(0, |acc, (i, b)| acc + ((*b as u8) << (7 - i))))
  30. .collect();
  31. String::from_utf8(us).unwrap_or(String::new())
  32. }
  33. }
  34. fn main() {
  35. let b64 = B64::new();
  36. let p = |s| {
  37. let e = b64.encode(s);
  38. let d = b64.decode(e.as_str());
  39. println!("{}\n{}\n{}\n", s, e, d);
  40. };
  41. p("ABCDEFG");
  42. p("Hello, World!");
  43. p("0123456789\"#$%&'()`=@");
  44. p("💖");
  45. }
  46.  
Success #stdin #stdout 0s 4496KB
stdin
Standard input is empty
stdout
ABCDEFG
QUJDREVGRw==
ABCDEFG

Hello, World!
SGVsbG8sIFdvcmxkIQ==
Hello, World!

0123456789"#$%&'()`=@
MDEyMzQ1Njc4OSIjJCUmJygpYD1AA===
0123456789"#$%&'()`=@

💖
8J+Slg==
💖