Size: 3581 bytes.


  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
#include "numeronym.h"

#include <stdbool.h>
#include <stddef.h>
#include <stdio.h>
#include <stdlib.h>

bool IsNumeronym(char* pattern, size_t m, char* input,
                 size_t n) {
  if (pattern == NULL || input == NULL) {
    fprintf(stderr, "pattern or input parameter is null\n");
    return false;
  }
  size_t i = 0;  // pattern
  size_t j = 0;  // input
  while (i < m && j < n) {
    if (IsAlpha(pattern[i]) && pattern[i] == input[j]) {
      i++;
      j++;
    } else if (IsNumeral(pattern[i])) {
      size_t number = 0;
      if (!TryParseUInt(pattern, &i, m, &number)) {
        fprintf(stderr, "Failed to parse uint.\n");
        return false;
      }
      i++;  // increment i to move past the last digit
      if (!ScrollForward(input, &j, n, number)) {
        fprintf(stderr, "Unable to scroll forward.\n");
        return false;
      }
    } else {
      fprintf(stderr,
              "Invalid character in pattern: "
              "pattern[i=%zu]=%c, input[j=%zu]=%c\n",
              i, pattern[i], j, input[j]);
      return false;
    }
  }
  return (i == m) && (j == n);
}

bool InArrayBounds(const char* s, size_t n, size_t i) {
  return i < n;
}

bool IsAlpha(char c) {
  return ('a' <= c && c <= 'z') || ('A' <= c && c <= 'Z');
}

bool IsNumeral(char c) { return ('0' <= c && c <= '9'); }

bool TryParseUInt(char* pattern, size_t* i, size_t m,
                  size_t* number) {
  if (pattern == NULL || i == NULL || number == NULL) {
    fprintf(stderr,
            "pattern, i, and number pointer arguments may "
            "not be null.");
    return false;
  }
  // Find length of the uint.
  size_t local_i = *i;
  size_t uint_char_count = 0;
  while (local_i < m && IsNumeral(pattern[local_i])) {
    uint_char_count++;
    local_i++;
  }
  if (uint_char_count == 0) {
    fprintf(stderr, "No digits found to parse as uint.\n");
    return false;
  }

#if 0
  // From ChatGPT:
  // Parse digits forward.
  size_t value = 0;
  for (size_t idx = *i; idx < *i + uint_char_count; idx++) {
    char c = pattern[idx];
    if (!IsNumeral(c)) {
      fprintf(stderr,
              "pattern[idx=%zu]=%c is unexpectedly not a "
              "numeral.\n",
              idx, c);
      return false;
    }
    size_t digit = (size_t)(c - '0');
    value = value * 10 + digit;
  }
#else
  size_t value = 0;
  // Add digits from the back.
  size_t parsing_i = *i + uint_char_count - 1;
  size_t tens_mult = 1;
  while (parsing_i >= *i && parsing_i < m) {
    char c = pattern[parsing_i];
    if (!IsNumeral(c)) {
      fprintf(
          stderr,
          "pattern[parsing_i=%zu]=%c is unexpectedly not a "
          "numeral.\n",
          parsing_i, c);
      return false;
    }
    size_t digit = c - '0';
    value += digit * tens_mult;
    parsing_i = parsing_i - 1ul;
    tens_mult *= 10;
  }
#endif

  // Assign out params.
  *i = *i + uint_char_count - 1;  // leave i on last digit
  *number = value;
  return true;
}

bool ScrollForward(const char* input, size_t* j, size_t n,
                   size_t number) {
  if ((*j + number) > n) {
    fprintf(stderr,
            "Scroll function found that index will go out "
            "of bounds: (*j + number) > n, for *j=%zu, "
            "number=%zu, n=%zu.\n",
            *j, number, n);
    return false;
  }
  size_t local_j = *j;
  for (size_t count = 0; count < number; count++) {
    if (!InArrayBounds(input, n, local_j)) {
      fprintf(stderr,
              "Index is unexpectedly out of bounds.\n");
      return false;
    }
    local_j++;
  }
  *j = local_j;
  return true;
}
v0 (commit) © 2025 @p13i.io | Load balancer proxied to: cs-code-viewer-3:8080 in 5ms.