Unfamiliar with specific data-type conversion used

I wrote up a project to write text and store it on EEPROM for display on LCD and serial. For this application I used String() and not the C++ implementation. I realize the better practice is to use “string” but for expediency i used the prior.

The problem I ran into was reading the characters from EEPROM always resulted in the ASCII format of the letter. But on here I saw someone’s’ code for displaying the letters and I am interested in how it works because I have never seen the syntax for something like it before and would appreciate an explanation. Specifically, lines 46 and 47 where “(char)” is placed right before the call to memory.

// Ensure Serial Monitor has "No Line Ending"

/*
The purpose of this code is to be able to both enter text into the serial command line, store it to memory, and display it on the LCD screen.
If the text exceeds 16 chars, it is rejected by the code (ver I)

"newWordFlag" ensues the word doesn't print continously. "printFlip" ensures the word only prints once
*/
#include <EEPROM.h>
#include <LiquidCrystal.h>
LiquidCrystal lcd(12,11,10,9,8,7);
bool newWordFlag = false;
bool printFlip = false;

int len;

void setup() {
  Serial.begin(9600);
  lcd.begin(16,2);
  lcd.setCursor(0,1);
}

void loop() {
  len = EEPROM.read(24);
  if (Serial.available() > 0){ // Captures input from serial
    newWordFlag = true;
    printFlip = false;
    lcd.clear();
    String line_1 = Serial.readString();

    len = line_1.length();

    EEPROM.write(24,len);
    for (int i=0; i<=len; i++){
      EEPROM.write(25+i, line_1[i]);
    }
  }
  else{
    newWordFlag = false;
  }

  if (newWordFlag == false && printFlip == false){
    printFlip = true;
    //newWordFlag = true;
     for (int j=25; j<=len+24; j++){
      lcd.print((char)EEPROM.read(j));
      Serial.print((char)EEPROM.read(j));
      //Serial.println();
    }
    //Serial.print("Broken"); // Used to test conditional, Enters "for"?
    //Serial.println();
  }
  
  

        
}


    
      




That is a type cast.
It converts one type into another...
Sometimes that is ok.
Sometimes it is ok, but you loose some info...
(int)7.6 will case the .6 to get lost.
It should always be used with care!.

And @david_2018 was so kind to explain why it is needed here....

      lcd.print((char)EEPROM.read(j));
      Serial.print((char)EEPROM.read(j));

The EEPROM.read() function returns an uint8_t. Using that directly as the argument for print() will result in the decimal value of the ASCII code being printed. The (char) is casting the return value from EEPROM.read() to a char data type, so that print() will treat it as a printable ASCII character.

By the way: this is an explicit type cast.
It is preferred over an implicit type cast. Because it tells that you intend to do the cast...

Implicit cast:
float a= 4.5;
int b = a;

Explicit cast:
float a= 4.5;
int b = (int) a;

Better:
int b = trunc(a);

In C++ you can have multiple functions with the same name but they differ in the type or number of parameters they expect. So based on what is passed to the function when you call its name, a specific implementation is called.

This is the case with the print() function. It has many variants (we call that overloading the function)

So you see that if you pass a char parameter, it’s not the same function as if you pass a number for example.

In your code, as explained by @david_2018, the cast is needed to call the right print function which will print the matching ASCII char instead than its numerical code value.

Try this to see how it works


void f(int x) {
  Serial.print("int version: ");
  Serial.println(x);
}

void f(char c) {
  Serial.print("char version: ");
  Serial.println(c);
}

void setup() {
  Serial.begin(115200);
  f(65);
  f('A');
  f((char) 65); // 65 is the ascii code for the letter A
}

void loop() {}