1

This is unfinished code for driving a 4 digit 7 segment display. When I run my data function that should output the data to send to the shift register, I get a very weird output.

0 00111111 1 00111111 2 00111111 3 00111111 After this, it repeats.

I am under the impression that it should give this output: 0111111. I have tried to replace the data loop starting number with 7 which I think is correct, but it still gives me a weird output with the weird starting numbers. Is there something I'm missing or is more information needed.

int chars[10][7] = {
  { 0, 1, 1, 1, 1, 1, 1 },
  { 0, 0, 0, 0, 1, 1, 0 },
  { 1, 0, 1, 1, 0, 1, 1 },
  { 1, 0, 0, 1, 1, 1, 1 },
  { 1, 1, 0, 0, 1, 1, 0 },
  { 1, 1, 0, 1, 1, 0, 1 },
  { 1, 1, 1, 1, 1, 0, 1 },
  { 0, 0, 0, 0, 1, 1, 1 },
  { 1, 1, 1, 1, 1, 1, 1 },
  { 1, 1, 0, 1, 1, 1, 1 }
};

int nums[4][4] = {
  { 1, 0, 0, 0 },
  { 0, 1, 0, 0 },
  { 0, 0, 1, 0 },
  { 0, 0, 0, 1 }
};

int data = 8;
int clk = 10;
int latch = 9;
int light = 0;



void setup() {
  Serial.begin(9600);
  pinMode(data, OUTPUT);
  pinMode(clk, OUTPUT);
  pinMode(latch, OUTPUT);
  initilize();
  delay(1000);
}





void initilize() {
  start();
  for (int i = 12; i > -1; i--) {
    digitalWrite(data, 0);
    digitalWrite(clk, 1);
    digitalWrite(clk, 0);
  }
  Latch();
}

void numprocess() {
  long number = millis();
  long size = 0;
  long num1 = 0;
  long num2 = 0;
  long num3 = 0;
  long num4 = 0;
  number = millis();
  size = trunc(log10(number));
  num1 = fmod(number / pow(10, size - 0), 10);
  num2 = fmod(number / pow(10, size - 1), 10);
  num3 = fmod(number / pow(10, size - 2), 10);
  num4 = fmod(number / pow(10, size - 3), 10);
}

void Light() {
  Serial.println(light);
  light++;
  if (light >= 4) {
    light = { 0 };
  };
}

void start() {
  digitalWrite(data, 0);
  digitalWrite(clk, 0);
  digitalWrite(latch, 0);
}

void Data() {
  for (int j = 8; j >= 1; j--) {

    Serial.println(chars[0][j]);

  };
}

void Latch() {
  digitalWrite(latch, 1);
  digitalWrite(latch, 0);
}


void loop() {
  start();
  Light();
  Serial.println();
  Data();
  delay(10000);
  Latch();
  start();
}
2
  • 1
    add debugging code so that you know which part of the program is printing unexpected values Commented May 1, 2025 at 1:22
  • 1
    Do not use log10() and pow() for integer arithmetic: these floating point functions are slow and produce rounding errors. Use repeated division and modulo instead, like: for(int i=0;i<4;++i) {digits[i]=number%10; number/=10;} Commented May 1, 2025 at 8:44

1 Answer 1

3

Your error is the index into the chars[10][7] array. Your code uses indexes from 8 down to and including 1. But the second dimension holds only 7 elements, with indexes in the range 0 to 6.

This is a corrected version of the function Data():

const int DIGITS = 10;
const int SEGMENTS_PER_DIGIT = 7;

int chars[DIGITS][SEGMENTS_PER_DIGIT] = {
  //...
};

//...

void Data() {
  for (int j = SEGMENTS_PER_DIGIT - 1; j >= 0; j--) {
    Serial.println(chars[0][j]);
  }
}

Why does the out-of-bounds access work at all and produce the observed output?

The two-dimensional array chars[10]7] holds all its elements directly in sequence. Therefore chars[0][8] accesses actually chars[1][1] and chars[0][7] accesses actually chars[1][0], which are both 0. These are the two zeroes you see printed. The following ones are the 1s in chars[0][6] to chars[0][1].

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.