0

I'm trying to write the substitution cipher but, a part of it, in particular the one where it sees me if the inserted alphabet is composed only of text characters "a ... z", doesn't work me. Could you tell me why the isalpha function (alfabeto_sostitutivo), although I insert the normal alphabet, gives me 0 as a result? Thanks in advance for the time spent.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>

int main () {

  int  caratteri_diversi_1 = 0, caratteri_diversi_2 = 0, b = 0, tutti_alpha = 0, alpha_minuscoli = 0,            alpha_maiuscoli = 0;
  char alfabeto_sostituzione [27];

  printf ("Inserisci l'alfabeto di criptazione (inglese):\n");
  fgets  (alfabeto_sostituzione, sizeof(alfabeto_sostituzione), stdin);
    if (strlen(alfabeto_sostituzione)==26) //se la lunghezza dell'alfabeto sostitutivo è giusta
      {
        printf("I due alfabeti sono lunghi uguale\n");
        for (int c=0; alfabeto_sostituzione[c] != '\0'; c++)
          {
            if (isalpha(alfabeto_sostituzione[c])==1)
              alpha_minuscoli++;
            else if (isalpha(alfabeto_sostituzione[c])==2)
              alpha_maiuscoli++;
          }
        tutti_alpha = alpha_minuscoli + alpha_maiuscoli;
        printf("alpha_minuscoli: %d\n",alpha_minuscoli);
        printf("alpha_maiuscoli: %d\n",alpha_maiuscoli);
        printf("tutti_alpha: %d\n",tutti_alpha);
        if (tutti_alpha < 26 )
          printf("L'alfabeto inserito NON contiene solo caratteri dell'alfabeto\n");
      }
  }

By filling in the program, the following text is returned:

Inserisci l'alfabeto di criptazione (inglese):

abcdefghijklmnopqrstuvwxyz

I due alfabeti sono lunghi uguale

alpha_minuscole: 0 alpha_maiuscole:0

tutti_alpha: 0

L'alfabeto inserito NON contiene solo caratteri dell'alfabeto

  • 6
    Because you are not comparing it to zero? You are comparing it to `1`. And it is only guaranteed to produce *zero* or *non-zero*. And for some reason you are even comparing it to `2`? – Eugene Sh. Nov 12 '19 at 21:10
  • 1
    Note that `isalpha(str[c])`, where the argument `str` is an array of `char`, is not safe. `char` can be signed, which means it can have negative values. The input to `isalpha` (and other `ctype.h` functions) must either be a non-negative value (in the range 0 to UCHAR_MAX), or else the value of the negative constant `EOF` (not just any negative value). Basically, the input convention of these functions is derived from the return value convention of the `getc` function; they are geared toward classifying input characters read with `getc`. – Kaz Nov 12 '19 at 21:26
  • Because I had already tried to put 0 but it didn't seem to read me and therefore to verify it I tried to see the opposite case. I used 1 and 2 because I read that the function gives me 1 if the characters I read are tiny, while it returns 2 if the characters I read are capitalized. – CrisUnipg Nov 12 '19 at 21:32
  • 1
    *I read that the function gives me 1 if the characters I read are tiny, while it returns 2 if the characters I read are capitalized* - No way. Where did you read it? – Eugene Sh. Nov 12 '19 at 21:33
  • Kaz - And if I use an unsigned char could it works? – CrisUnipg Nov 12 '19 at 21:35
  • Eugene - I have read it here [https://www.programiz.com/c-programming/library-function/ctype.h/isalpha] – CrisUnipg Nov 12 '19 at 21:37
  • So you didn't read it carefully. It has the note right after the snippet you are probably referring to: *Note: You can get a different non-zero integer when alphabetic character is passed to isalpha() on your system. But, when you pass non-alphabetic character to isalpha(), it always returns 0.* – Eugene Sh. Nov 12 '19 at 21:38
  • Yes, but it doesn't works... – CrisUnipg Nov 12 '19 at 21:43
  • Then you should post the code which is at least attempting to conform with the proper function usage, and ask why it does not work. The posted code is not conforming. – Eugene Sh. Nov 12 '19 at 21:45
  • The problems you might have with signed chars can be eliminated by declaring your array as `unsigned char alfabeto_sostituzione[26+1]`. Or alternatively, by casting the argument to `isalpha` to an unsigned char, as in `isalpha((unsigned char) ch)`. – David R Tribble Nov 12 '19 at 22:15
  • If you like to detect lowercase and uppercase characters, try [`islower()`](https://en.cppreference.com/w/c/string/byte/islower) and [`isupper()`](https://en.cppreference.com/w/c/string/byte/isupper). --- BTW, the link in your comment to Eugene is dead for me. – the busybee Nov 13 '19 at 06:46

1 Answers1

1
  • isalpha(argument) and other related functions declared in ctype.h return a non-zero(true) if the argument satisfies the condition described, and zero(false) if not.

Since you are checking for lower and upper case characters, the ctype library already has functions islower(argument) and isupper(argument) defined. You could use them in tandem with the isaplha function, like so......

for (int c=0; alfabeto_sostituzione[c] != '\0'; c++)
      {
        if (isalpha(alfabeto_sostituzione[c]))
          {
            if(islower(alfabeto_sostituzione[c]))
              alpha_minuscoli++;
            else
              alpha_maiuscoli++;
          } 
      }
Lily AB
  • 392
  • 2
  • 6