perfaware/part2: Extract the strings containing the haversine points

This commit is contained in:
doyle 2023-07-01 22:32:50 +10:00
parent f8ac671e3a
commit 1f9a9bdc21
5 changed files with 102 additions and 11 deletions

View File

@ -321,4 +321,7 @@ REM Build ======================================================================
pushd %part2_build_dir% pushd %part2_build_dir%
cl %part2_dir%\haversine_generator.c /W4 /WX /Z7 /nologo /Fe:haversine_generator_debug || exit /b 1 cl %part2_dir%\haversine_generator.c /W4 /WX /Z7 /nologo /Fe:haversine_generator_debug || exit /b 1
cl %part2_dir%\haversine_generator.c /W4 /WX /Z7 /nologo /O2 /Fe:haversine_generator_release || exit /b 1 cl %part2_dir%\haversine_generator.c /W4 /WX /Z7 /nologo /O2 /Fe:haversine_generator_release || exit /b 1
cl %part2_dir%\haversine.c /W4 /WX /Z7 /nologo /Fe:haversine_debug || exit /b 1
cl %part2_dir%\haversine.c /W4 /WX /Z7 /nologo /O2 /Fe:haversine_release || exit /b 1
popd popd

View File

@ -8,6 +8,26 @@
#include <math.h> #include <math.h>
#include "listing_0065_haversine_formula.cpp" #include "listing_0065_haversine_formula.cpp"
typedef struct Str8FindResult {
bool found;
HAV_Str8 match;
HAV_Str8 match_to_end_of_buffer;
} Str8FindResult;
Str8FindResult FindFirstCharThatLooksLikeANumber(HAV_Str8 buffer)
{
Str8FindResult result = {0};
for (size_t index = 0; !result.found && index < buffer.size; index++) {
if (HAV_CharIsDigit(buffer.data[index]) || buffer.data[index] == '+' || buffer.data[index] == '-') {
result.found = true;
result.match = (HAV_Str8){.data = buffer.data + index, .size = 1};
result.match_to_end_of_buffer = (HAV_Str8){.data = result.match.data, .size = buffer.size - index};
break;
}
}
return result;
}
#define PRINT_USAGE HAV_PrintLnFmt("Usage: %s [haversine_input.json] [answers.f64]", argv[0]) #define PRINT_USAGE HAV_PrintLnFmt("Usage: %s [haversine_input.json] [answers.f64]", argv[0])
int main(int argc, char **argv) int main(int argc, char **argv)
{ {
@ -20,15 +40,48 @@ int main(int argc, char **argv)
HAV_Str8 arg_json = {argv[1], strlen(argv[1])}; HAV_Str8 arg_json = {argv[1], strlen(argv[1])};
HAV_Str8 arg_answers = {0}; HAV_Str8 arg_answers = {0};
if (argc == 3) { if (argc == 3)
arg_answers = {.data = argv[2], .size = strlen(argv[2])}; arg_answers = (HAV_Str8){.data = argv[2], .size = strlen(argv[2])};
HAV_Buffer buffer = HAV_FileRead(arg_json.data);
if (!HAV_BufferIsValid(buffer))
return 0;
size_t pair_count = 0;
HAV_Str8 json_it = (HAV_Str8){.data = buffer.data, .size = buffer.size};
for (;; pair_count++) {
HAV_Str8BinarySplitResult x0_key = HAV_Str8_BinarySplit(json_it, HAV_STR8("x0"));
if (!x0_key.rhs.size)
break;
Str8FindResult x0_find_value = FindFirstCharThatLooksLikeANumber(x0_key.rhs);
HAV_Str8BinarySplitResult x0_value = HAV_Str8_BinarySplit(x0_find_value.match_to_end_of_buffer, HAV_STR8(","));
HAV_Str8BinarySplitResult y0_key = HAV_Str8_BinarySplit(x0_value.rhs, HAV_STR8("y0"));
Str8FindResult y0_find_value = FindFirstCharThatLooksLikeANumber(y0_key.rhs);
HAV_Str8BinarySplitResult y0_value = HAV_Str8_BinarySplit(y0_find_value.match_to_end_of_buffer, HAV_STR8(","));
HAV_Str8BinarySplitResult x1_key = HAV_Str8_BinarySplit(y0_value.rhs, HAV_STR8("x1"));
Str8FindResult x1_find_value = FindFirstCharThatLooksLikeANumber(x1_key.rhs);
HAV_Str8BinarySplitResult x1_value = HAV_Str8_BinarySplit(x1_find_value.match_to_end_of_buffer, HAV_STR8(","));
HAV_Str8BinarySplitResult y1_key = HAV_Str8_BinarySplit(x1_value.rhs, HAV_STR8("y1"));
Str8FindResult y1_find_value = FindFirstCharThatLooksLikeANumber(y1_key.rhs);
HAV_Str8BinarySplitResult y1_value = HAV_Str8_BinarySplit(y1_find_value.match_to_end_of_buffer, HAV_STR8("}"));
HAV_PrintLnFmt("{x0: %.*s, y0: %.*s, x1 %.*s, y1: %.*s}",
HAV_STR8_FMT(x0_value.lhs),
HAV_STR8_FMT(y0_value.lhs),
HAV_STR8_FMT(x1_value.lhs),
HAV_STR8_FMT(y1_value.lhs));
json_it = y1_value.rhs;
} }
size_t input_size = 0; size_t input_size = buffer.size;
size_t pair_count = 0; f64 haversine_sum = 0;
f64 haversine_sum = 0;
f64 reference_haversine_sum = 0; f64 reference_haversine_sum = 0;
f64 difference = 0; f64 difference = 0;
HAV_PrintLnFmt("Input size: %zu", input_size); HAV_PrintLnFmt("Input size: %zu", input_size);
HAV_PrintLnFmt("Pair count: %zu", pair_count); HAV_PrintLnFmt("Pair count: %zu", pair_count);
HAV_PrintLnFmt("Haversine sum: %f", haversine_sum); HAV_PrintLnFmt("Haversine sum: %f", haversine_sum);

View File

@ -99,8 +99,13 @@ int main(int argc, char **argv)
uint64_t random_seed = random_seed_u64_result.value; uint64_t random_seed = random_seed_u64_result.value;
uint64_t rng_state = random_seed; uint64_t rng_state = random_seed;
char json_file_name[1024];
char answers_file_name[1024];
snprintf(json_file_name, sizeof(json_file_name), "haversine_%zu_%s_%zu.json", point_count, point_generator == PointGenerator_Cluster ? "cluster" : "uniform", random_seed);
snprintf(answers_file_name, sizeof(json_file_name), "haversine_%zu_%s_%zu.f64", point_count, point_generator == PointGenerator_Cluster ? "cluster" : "uniform", random_seed);
HANDLE haversine_json_file_handle = CreateFile( HANDLE haversine_json_file_handle = CreateFile(
/*LPCSTR lpFileName*/ "haversine.json", /*LPCSTR lpFileName*/ json_file_name,
/*DWORD dwDesiredAccess*/ GENERIC_WRITE, /*DWORD dwDesiredAccess*/ GENERIC_WRITE,
/*DWORD dwShareMode*/ 0, /*DWORD dwShareMode*/ 0,
/*LPSECURITY_ATTRIBUTES lpSecurityAttributes*/ NULL, /*LPSECURITY_ATTRIBUTES lpSecurityAttributes*/ NULL,
@ -110,7 +115,7 @@ int main(int argc, char **argv)
); );
HANDLE haversine_f64_file_handle = CreateFile( HANDLE haversine_f64_file_handle = CreateFile(
/*LPCSTR lpFileName*/ "haversine.f64", /*LPCSTR lpFileName*/ answers_file_name,
/*DWORD dwDesiredAccess*/ GENERIC_WRITE, /*DWORD dwDesiredAccess*/ GENERIC_WRITE,
/*DWORD dwShareMode*/ 0, /*DWORD dwShareMode*/ 0,
/*LPSECURITY_ATTRIBUTES lpSecurityAttributes*/ NULL, /*LPSECURITY_ATTRIBUTES lpSecurityAttributes*/ NULL,

View File

@ -27,12 +27,34 @@ HAV_Str8ToU64Result HAV_Str8_ToU64(HAV_Str8 string)
return result; return result;
} }
HAV_Str8BinarySplitResult HAV_Str8_BinarySplit(HAV_Str8 buffer, HAV_Str8 find)
{
HAV_Str8BinarySplitResult result = {0};
result.lhs = buffer;
for (size_t index = 0; (index + find.size) <= buffer.size; index++) {
HAV_Str8 check = {buffer.data + index, find.size};
if (HAV_Str8_Equals(find, check)) {
result.lhs.size = index;
result.rhs.data = check.data + find.size;
result.rhs.size = buffer.size - (index + find.size);
break;
}
}
return result;
}
bool HAV_CharIsWhiteSpace(char ch) bool HAV_CharIsWhiteSpace(char ch)
{ {
bool result = ch == ' ' || ch == '\n' || ch == '\r' || ch == '\t'; bool result = ch == ' ' || ch == '\n' || ch == '\r' || ch == '\t';
return result; return result;
} }
bool HAV_CharIsDigit(char ch)
{
bool result = ch >= '0' && ch <= '9';
return result;
}
#pragma warning(push) #pragma warning(push)
#pragma warning(disable: 4146) // warning C4146: unary minus operator applied to unsigned type, result still unsigned #pragma warning(disable: 4146) // warning C4146: unary minus operator applied to unsigned type, result still unsigned
uint32_t HAV_PCG32_Pie (uint64_t *state) uint32_t HAV_PCG32_Pie (uint64_t *state)

View File

@ -15,6 +15,7 @@
#define HAV_ARRAY_UCOUNT(array) sizeof((array)) / sizeof((array)[0]) #define HAV_ARRAY_UCOUNT(array) sizeof((array)) / sizeof((array)[0])
#define HAV_CAST(Type) (Type) #define HAV_CAST(Type) (Type)
#define HAV_MIN(a, b) ((a) < (b) ? (a) : (b))
typedef float f32; typedef float f32;
typedef double f64; typedef double f64;
@ -40,13 +41,20 @@ typedef struct HAV_Str8ToU64Result {
uint64_t value; uint64_t value;
} HAV_Str8ToU64Result; } HAV_Str8ToU64Result;
typedef struct HAV_Str8BinarySplitResult {
HAV_Str8 lhs;
HAV_Str8 rhs;
} HAV_Str8BinarySplitResult;
#define HAV_STR8(string) (HAV_Str8){.data = (string), .size = HAV_ARRAY_UCOUNT(string) - 1 } #define HAV_STR8(string) (HAV_Str8){.data = (string), .size = HAV_ARRAY_UCOUNT(string) - 1 }
#define HAV_STR8_FMT(string) (int)((string).size), (string).data #define HAV_STR8_FMT(string) (int)((string).size), (string).data
bool HAV_Str8_Equals(HAV_Str8 lhs, HAV_Str8 rhs); bool HAV_Str8_Equals(HAV_Str8 lhs, HAV_Str8 rhs);
HAV_Str8ToU64Result HAV_Str8_ToU64(HAV_Str8 string); HAV_Str8ToU64Result HAV_Str8_ToU64(HAV_Str8 string);
HAV_Str8BinarySplitResult HAV_Str8_BinarySplit(HAV_Str8 buffer, HAV_Str8 find);
bool HAV_CharIsWhiteSpace(char ch); bool HAV_CharIsWhiteSpace(char ch);
bool HAV_CharIsDigit(char ch);
// NOTE: PCG32 // NOTE: PCG32
// ============================================================================ // ============================================================================