J'ai écrit la fonction suivante pour allouer dynamiquement une chaîne d'entrée lors de la frappe, sans demander à l'utilisateur combien de caractères elle est longue.

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

char* dyninp (char str[], int *n) {
  char ch;
  int i = 0;
  do {
    ch = getchar();
    str = (char *) realloc(str, (i+1)*sizeof(char));
    str[i] = ch;
    i++;
  } while (ch != '\n');

  /*substitute '\n' with '\0'*/
  str[i-1] = '\0';

  if (n != NULL) {
    /*i contains the total lenght, including '\0'*/
    *n = i-1;
  }

  /*because realloc changes array's address*/
  return str;
}

/*it is called in this way:
char *a;
int n;
a = dyninp (a, &n);
*/

Ce code fonctionne, mais j'ai quelques questions à ce sujet:

  1. Pourquoi ça marche?
    Je ne comprends pas pourquoi, lorsque je l'exécute, je peux également supprimer des caractères avant d'appuyer sur Entrée. La fonction getchar() ne lit qu'un seul caractère à chaque itération, qui est écrit dans le tableau, alors comment pourrais-je en supprimer?
    Si getchar() supprime le caractère précédent lorsqu'il reçoit '\ 127', alors la boucle devrait continuer à s'exécuter comme avec n'importe quel autre caractère. Mais cela ne se produit pas, car lorsque la boucle se termine, "i" contient toujours le nombre exact d'éléments.

  2. Mon code est-il efficace? Si ce n'est pas le cas, comment pourrais-je l'améliorer (même en utilisant des fonctions intégrées)?

1
Rat Salad 17 janv. 2017 à 00:30

2 réponses

Meilleure réponse
  1. À moins que vous ne mettiez le terminal en mode «brut», le système d'exploitation ne met pas l'entrée à la disposition de l'application tant que vous n'appuyez pas sur Entrée. La modification des entrées est gérée par le système d'exploitation. Lorsque vous appelez getchar(), il lit un caractère dans ce tampon d'entrée, pas directement depuis le terminal.

  2. Il existe une fonction POSIX getline() qui fait le même chose.

1
Barmar 16 janv. 2017 à 21:52

Réponse à la première question:

La raison en est probablement la mise en mémoire tampon dans le pilote du terminal. Une brève explication est fournie ici dans la section des notes. La fonction getchar() ne reçoit aucune entrée tant qu'une ligne n'a pas été validée par l'utilisateur dans le terminal lorsqu'elle reçoit la chaîne entière et la renvoie caractère par caractère. La suppression est donc une caractéristique de votre terminal, pas de votre programme.

1
Nils_M 16 janv. 2017 à 21:51