Skip to content

suyash/ulid

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

63 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

ulid

.github/workflows/test.yml

C++ port of oklog/ulid and alizain/ulid.

There are 2 implementations, the first in ulid_uint128.hh uses a __uint128_t to represent a ULID.

The second in ulid_struct.hh encapsulates a 16 byte array in a struct, and uses that to represent a ULID

ulid.hh essentially (tries to) see if __uint128_t exists, in which case it imports the definition in ulid_uint128.hh, otherwise it imports the implementation in ulid_struct.hh.

The __uint128_t version seems to be faster, some benchmarks below and more extensive ones on travis.

Usage

#include <ulid.hh> ... ulid::ULID ulid = ulid::Create(1484581420, []() { return 4; }); std::string str = ulid::Marshal(ulid); std::cout << str << '\n'; // 0001C7STHC0G2081040G208104

API

ulid::ULID

The wrapper type for a __uint128_t / 16 byte array representing a ULID.

void ulid::EncodeTime(time_t, ULID&)

encodes passed time in first 6 bytes of a ULID.

void ulid::EncodeTimeNow(ULID&)

encodes std::time(nullptr) as time.

void ulid::EncodeTimeSystemClockNow(ULID&)

encodes std::chrono::system_clock::now() by taking the timestamp in milliseconds.

void ulid::EncodeEntropy(const std::function<uint8_t()>&, ULID&)

sets the last 10 bytes as the values generated using the passed random byte generator.

void ulid::EncodeEntropyRand(ULID&)

sets the entropy using std::rand.

void ulid::EncodeEntropyMt19937(std::mt19937& generator, ULID& ulid)

sets the entropy by generating values from a std::mt19937 generator, initializes a std::uniform_int_distribution on each invocation.

void ulid::Encode(time_t, const std::function<uint8_t()>&, ULID&)

EncodeTime + EncodeEntropy

void ulid::EncodeNowRand(time_t, const std::function<uint8_t()>&, ULID&)

EncodeTimeNow + EncodeEntropyRand

ulid::ULID ulid::Create(time_t, const std::function<uint8_t()>&)

creates a fresh ULID using the passed timestamp and generator.

void ulid::CreateNowRand()

Create:Encode::CreateNowRand:EncodeNowRand

void ulid::MarshalTo(const ULID&, char[26])

Marshals the ulid into the passed character array.

std::string ulid::Marshal(const ULID&)

Marshals and generates std::string.

void ulid::MarshalBinaryTo(const ULID&, uint8_t[16])

Marshals the ulid into the passed byte array.

std::vector<uint8_t> ulid::MarshalBinary(const ULID&)

Marshals and generates std::vector<uint8_t>.

void ulid::UnmarshalFrom(const char[26], ULID&)

Unmarshals the passed character array into the ulid.

ULID ulid::Unmarshal(const std::string&)

Creates a new ULID by Unmarshaling the passed string.

void ulid::UnmarshalBinaryFrom(const uint8_t[26], ULID&)

Unmarshals the passed byte array into the ulid.

ULID ulid::UnmarshalBinary(const std::vector<uint8_t>&)

Creates a new ULID by Unmarshaling the passed vector.

time_t ulid::Time(const ULID&)

Extracts the timestamp used to create the ULID.

Benchmarks

Ubuntu Xenial (16.04), clang++-8

From https://travis-ci.org/suyash/ulid/jobs/475187043

ulid_uint128

./ulid_uint128_bench.out --benchmark_out_format=console 2019-01-04 07:11:24 Running ./ulid_uint128_bench.out Run on (2 X 2500 MHz CPU s) CPU Caches: L1 Data 32K (x1) L1 Instruction 32K (x1) L2 Unified 256K (x1) L3 Unified 30720K (x1) Load Average: 0.98, 0.51, 0.21 -------------------------------------------------------------------- Benchmark Time CPU Iterations -------------------------------------------------------------------- EncodeTime 23.2 ns 23.2 ns 30323833 EncodeTimeNow 26.8 ns 26.7 ns 25925285 EncodeTimeSystemClockNow 96.4 ns 96.4 ns 7366207 EncodeEntropy 209 ns 209 ns 3363959 EncodeEntropyRand 100 ns 100 ns 6875073 EncodeEntropyMt19937 470 ns 469 ns 1481254 Encode 231 ns 231 ns 3022655 EncodeNowRand 128 ns 128 ns 5346738 Create 238 ns 238 ns 2970710 CreateNowRand 133 ns 133 ns 5384520 MarshalTo 37.5 ns 37.5 ns 18655071 Marshal 83.7 ns 83.7 ns 8261322 MarshalBinaryTo 16.7 ns 16.7 ns 41790384 MarshalBinary 157 ns 157 ns 4464307 UnmarshalFrom 64.0 ns 63.9 ns 10822292 Unmarshal 113 ns 113 ns 6146163 UnmarshalBinaryFrom 64.8 ns 64.8 ns 10942429 UnmarshalBinary 248 ns 248 ns 2832217 Time 15.0 ns 15.0 ns 46389021 CompareULIDs 8.44 ns 8.44 ns 83106152 

ulid_struct

./ulid_struct_bench.out --benchmark_out_format=console 2019-01-04 07:11:43 Running ./ulid_struct_bench.out Run on (2 X 2500 MHz CPU s) CPU Caches: L1 Data 32K (x1) L1 Instruction 32K (x1) L2 Unified 256K (x1) L3 Unified 30720K (x1) Load Average: 0.99, 0.54, 0.22 -------------------------------------------------------------------- Benchmark Time CPU Iterations -------------------------------------------------------------------- EncodeTime 9.14 ns 9.13 ns 76851483 EncodeTimeNow 12.6 ns 12.6 ns 55315496 EncodeTimeSystemClockNow 73.5 ns 73.5 ns 9515669 EncodeEntropy 201 ns 201 ns 3480980 EncodeEntropyRand 196 ns 195 ns 3602452 EncodeEntropyMt19937 449 ns 449 ns 1560469 Encode 211 ns 211 ns 3352107 EncodeNowRand 204 ns 204 ns 3493016 Create 217 ns 217 ns 3214903 CreateNowRand 213 ns 213 ns 3271363 MarshalTo 34.1 ns 34.1 ns 20540465 Marshal 80.6 ns 80.5 ns 8743422 MarshalBinaryTo 17.6 ns 17.6 ns 39780449 MarshalBinary 154 ns 154 ns 4503322 UnmarshalFrom 33.3 ns 33.3 ns 20997275 Unmarshal 88.5 ns 88.4 ns 7957903 UnmarshalBinaryFrom 17.0 ns 17.0 ns 41314026 UnmarshalBinary 198 ns 198 ns 3541637 Time 14.9 ns 14.9 ns 46747210 CompareULIDs 20.6 ns 20.6 ns 34150306 

For a comparison across latest 3 versions of g++ and clang++ on linux and clang++ on mac, see https://travis-ci.org/suyash/ulid/builds/475187039

Hacking

The library uses googletest for tests and benchmark as benchmarks, which are built as submodules. In order to get those dependencies, clone recursively, i.e.

git clone -r https://github.com/suyash/ulid 

About

ulids in C++, Header Only

Topics

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Contributors 4

  •  
  •  
  •  
  •