Ir ao conteúdo
  • Cadastre-se

C Linguagem C problema em resolver o código


Andrah

Posts recomendados

:) 

Como está seu programa agora? Ainda precisa de algo?

 

Isso foi o que eu perguntei. 3 vezes agora desde antes do almoço. Poste o programa como está agora e alguma dificuldade que tenha.

 

Se se interessou por algo dessas "discussões meio paralelas" mas não compreendeu simplesmente como um ato de vingança "invada"  a discussão paralela e pergunte algo :)

  • Obrigado 1
Link para o comentário
Compartilhar em outros sites

1 minuto atrás, arfneto disse:

Como está seu programa agora? Ainda precisa de algo?

Sim precisa é que as funções não estão certas acho e ainda falta fazer algumas funções para colocar nos cases 

3 minutos atrás, arfneto disse:

Isso foi o que eu perguntei. 3 vezes agora desde antes do almoço. Poste o programa como está agora e alguma dificuldade que tenha.

O programa tá igual não estou conseguindo resolver 

//bibliotecas
#include <stdio.h>
#include <stdlib.h>
#include <locale.h>
#include <string.h>
#include <conio.h>
#include <time.h>

//Dados do funcionário
struct Funcionario {
    char nome[20];
    char NIF[20];
    char categoria[20];
    float salario;
    int Hora_Trabalhados;
};

// Para não atrapalhar o bom funcionamento
void menu ( struct Funcionario funcionario[], int n );

void pressioneEnter() {
    char c;

    do {
        c = getch();
    } while ( c != 13 );
}

void flush() {
    int c;
    /*Lê todos os caracteres até encontrar '\n' ou EOF:*/
    while( (c = getchar()) != '\n' && c != EOF );
}

void IncerirFuncionario ( struct Funcionario funcionario[], int n ) {
    system ( "COLOR 0F" );
    FILE *file; // cria variável ponteiro para o arquivo
    file = fopen ( "funcionarios.txt", "w" ); //abrindo o arquivo

    if ( file == NULL ) //testando se o arquivo foi realmente criado
        printf ( "\n-->Nao foi possivel abrir o fecheiro\n\n" );
    else {
        printf ( "\n\n\n\n\tUNICV \n\n" );
        printf ( "\n\n\n\t\tDigite o numero de Funcionarios que pretende registrar: " );
        scanf ( " %i", &n );
        flush ();
        system ( "cls" );
        static int i = 0;
        int y = n + i;

        if ( y > 99 )
            menu ( funcionario, n );

        printf ( "\n\n\n\t\t-------- INSCRIÇÃO DE FUNCIONÁRIO --------\n\n" );
        fprintf ( file, "\n\n\t----- LISTA DOS FUNCIONÁRIOS ----\n\n" );
        fprintf ( file, "\tNome      NIF 	  Salário     Categoria    Horas\n\n" );

        for ( ; i < y; i++ ) {
            system ( "COLOR 0B" );
            // para obter dados e armazenar no arquivo
            printf ( "\n\tDigite o nome do funcionário: " );
            scanf ( " %s", funcionario[i].nome );
            flush ();
            printf ( "\n\tDigite o NIF do funcionário: " );
            scanf ( " %s",funcionario[i].NIF );
            printf ( "\n\tDigite o salario do funcionario: " );
            scanf ( " %f", &funcionario[i].salario );
            flush ();
            printf ( "\n\tDigite a categoria do funcionário: " );
            scanf ( " %s", funcionario[i].categoria );
            printf ( "\n\tDigite a Hora trabalhados pelo funcionário: " );
            scanf ( " %d", &funcionario[i].Hora_Trabalhados );
            printf ( "\n\n" );
            //A Escrevendo no arquivo
            fprintf ( file, "\t%s \t %s \t %.1f \t %s\t %d\n", funcionario[i].nome, funcionario[i].NIF, funcionario[i].salario, funcionario[i].categoria, funcionario[i].Hora_Trabalhados );
        }

        printf ( "\n\t\t-------------------------<3--------------------------\n" );
        printf ( "\n\t Incritos com sucesso! \n\n\t Registado no fecheiro -> funcionarios.txt\n\n" );
        printf ( "\n\n\n\t\t\tPressione ENTER para Continuar->" );
        flush ();
        pressioneEnter();
        system ( "cls" );
        menu ( funcionario, y );
    }

    fclose ( file ); // para fechar o arquivo
}

void ImprimirFuncionarios ( struct Funcionario funcionario[], int n ) {
    FILE *file;

    file = fopen ( "C:\\Users\\alex\\Desktop\\ajuda\\funcionarios.txt", "r" );

    if ( file == NULL )
        printf ( "\n-->Nao foi possivel abrir o fecheiro\n\n" );

    else {
        int i;
        printf ( "\n\n\n\t\t------- LISTA DOS FUNCIONÁRIOS ------\n\n" );

        for ( i = 0; i < n; i++ ) {
            system ( "COLOR 0F" );
            fscanf ( file, " %s", funcionario[i].nome );
            fscanf ( file, " %s", funcionario[i].NIF );
            fscanf ( file, " %f", &funcionario[i].salario );
            fscanf ( file, " %s", funcionario[i].categoria );
            fscanf ( file, " %d horas", &funcionario[i].Hora_Trabalhados );
            printf ( "\n\tNome: %s", funcionario[i].nome );
            printf ( "\n\tNIF: %s", funcionario[i].NIF );
            printf ( "\n\tSalario: %.1f $00", funcionario[i].salario );
            printf ( "\n\tCategoria: %s", funcionario[i].categoria );
            printf ( "\n\tHoras de trabalho: %d horas", funcionario[i].Hora_Trabalhados );
            printf ( "\n\n----------------------------------------------------------\n" );
        }
    }

    printf ( "\n\n\n\t\t\tPressione ENTER para Continuar->" );
    flush ();
    pressioneEnter();
    system ( "cls" );
    fclose ( file );

}

void OrdenarFuncionario ( struct Funcionario *funcionario, int n ) {

    int i, j;
    struct Funcionario aux;

    for ( i = 1; i < n; i++ ) {
        aux = funcionario[i] ;

        for ( j = i; ( j > 0 ) && ( aux.salario < funcionario[j - 1].salario ); j-- ) {
            funcionario[j] = funcionario[j - 1];
            funcionario[j] = aux;
        }

    }

    printf ( "\n\n\n\t------- LISTA DOS FUNCIONÁRIOS POR ORDEM CRESCENTE ------\n\n" );

    for ( i = 0; i < n; i++ ) {

        printf ( "\n\tNome: %s", funcionario[i].nome );
        printf ( "\n\tNIF: %s", funcionario[i].NIF );
        printf ( "\n\tSalario: %.1f $00", funcionario[i].salario );
        printf ( "\n\tCategoria: %s", funcionario[i].categoria );
        printf ( "\n\tHoras de trabalho: %d horas", funcionario[i].Hora_Trabalhados );
        printf ( "\n\n----------------------------------------------------------\n" );

    }

    printf ( "\n\n\n\t\t\tPressione ENTER para Continuar->" );
    flush ();
    pressioneEnter();
    system ( "cls" );
}


void EliminarFuncionario ( struct Funcionario funcionario[], int n ) {
    FILE *file;

    //Abre o arquivo novamente para leitura
    file = fopen ( "funcionarios.txt", "r+" );

    if ( file == NULL )
        printf ( "\n-->Nao foi possivel abrir o fecheiro\n\n" );

    else {
        int i;
        char nif;
        char resp;
        printf ( "\n\tInforme o NIF do funcionario a ser Eliminado: " );
        scanf ( " %d", &nif );

        while ( funcionario[i].NIF == nif ) {

            if ( funcionario[i].ativo== 1 ) {

                printf ( "\n\tNome: %s", funcionario[i].nome );
                printf ( "\n\tNIF: %s", funcionario[i].NIF );
                printf ( "\n\tSalario: %.1f $00", funcionario[i].salario );
                printf ( "\n\tCategoria: %s", funcionario[i].categoria );
                printf ( "\n\tHoras de trabalho: %d horas", funcionario[i].Hora_Trabalhados );
                printf ( "\n\n----------------------------------------------------------\n" );
            }
            printf ( "\n\tDeseja realmente eliminar o Funcionário? S/N:" );
            scanf ( " %c", &resp );

            if ( ( resp == 'S' ) || ( resp == 's' ) ) {
                funcionario[i].ativo=0;
                printf ( "\n\tFuncionário eliminado com sucesso\n" );
                break;
            } else {
                if ( ( resp == 'N' ) || ( resp == 'n' ) ) {
                    printf ( "\tEliminação cancelada!\n" );
                    break;
                }
            }
        }

        i++;

        if ( i > 99 )
            printf ( "\n\n\t\tNIF não encontrado\n" );
    }

    fclose ( file );
    printf ( "\n\n\n\t\t\tPressione ENTER para Continuar->" );
    flush ();
    pressioneEnter();
    system ( "cls" );
}

void menu ( struct Funcionario funcionario[], int n ) {
    int op;

    do {
        system ( "COLOR 0F" ); //Menu
        printf ( "\n\n\t\t\t\t---> SISTEMA DE REGISTO E CONTROLE DE FUNCIONÁRIO \n\n" );
        printf ( "\n\t\t* 1 ------- INSERIR OS FUNCIONÁRIOS E ENVIA-LOS PARA O FICHEIRO ------------------------ *\n" );
        printf ( "\n\t\t* 2 ------- IMPRIMIR A LISTA DOS FUNCIONÁRIOS DO FICHEIRO ------------------------------ *\n" );
        printf ( "\n\t\t* 3 ------- IMPRIMIR OS FUNCIONÁRIOS POR CATEGORIA ------------------------------------- *\n" );
        printf ( "\n\t\t* 4 ------- GASTO DA UNIVERSIDADE COM OS FUNCIONÁRIOS ---------------------------------- *\n" );
        printf ( "\n\t\t* 5 ------- CALCULAR O SALÁRIO DE UM FUNCIONÁRIO X EM FUNÇÃO DO SEU SALÁRIO POR HORA --- *\n" );
        printf ( "\n\t\t* 6 ------- ORDENAR FUNCIONÁRIO NA ORDEM CRESCENTE ------------------------------------- *\n" );
        printf ( "\n\t\t* 7 ------- IMPRIMIR OS FUNCIONÁRIOS COM SALÁRIO MAIOR QUE 75000$ ---------------------- *\n" );
        printf ( "\n\t\t* 8 ------- ELIMINAR UM FUNCIONÁRIO A PARTIR DO Nº DO NIF ------------------------------ *\n" );
        printf ( "\n\t\t* 0 ------- Sair\n\n" );
        printf ( "\n\tEscolha uma opcao: " );
        scanf ( " %d", &op );
        printf ( "\n" );

        switch ( op ) {
        case 0:
            printf ( "\t\t\t\t\t\t\t\t\t\t-> Saindo... \n" );
            printf ( "\tPressione ENTER para Sair->" );
            flush ();
            pressioneEnter();
            system ( "cls" );
            break;

        case 1:
            system ( "cls" );
            IncerirFuncionario ( funcionario, n );
            break;

        case 2:
            system ( "cls" );
            ImprimirFuncionarios ( funcionario, n );
            break;

        case 6:
            system ( "cls" );
            OrdenarFuncionario ( funcionario, n );
            break;

        case 8:
            system ( "cls" );
            EliminarFuncionario ( funcionario, n );
            break;

        default:
            system ( "COLOR C0" );
            printf ( "\n\t\t\t\t*-*-*-*-- ERRO --> Numero INVALIDO!\n\n" );
            printf ( "\n\tPressione ENTER para Tentar Novamente->" );
            flush ();
            pressioneEnter();
            system ( "cls" );
        }
    } while ( op != 0 );

}
int main() {
    setlocale ( LC_ALL, "Portuguese" );
    struct Funcionario funcionario[100];
    int n;
    struct Funcionario* p = ( struct Funcionario * ) malloc ( sizeof ( struct Funcionario ) );

    if ( p == NULL ) {
        printf ( "\n\t ERRO MEMÓRIA INSUFICIENTE!\n" );
        exit ( 1 ); //Terminar o programa
    }

    system ( "COLOR F0" ); //Abertura do programa
    printf ( "\n\n\n\n\n\t\t\t....................................................................\n" );
    printf ( "\n\t\t\t\t----> SISTEMA DE REGISTO E CONTROLE DE FUNCIONÁRIO \n" );
    printf ( "\n\t\t\t.....................................................................\n\n\n\n\n" );
    printf ( "\n\t\t\t                                                                      UNICV \n\n" );
    printf ( "\n\tPressione ENTER 2 vezes para iniciar->" );
    flush ();
    pressioneEnter();
    system ( "cls" );
    menu ( funcionario, n );
    free ( p );
    return 0;

 

6 minutos atrás, arfneto disse:

Se se interessou por algo dessas "discussões meio paralelas" mas não compreendeu simplesmente como um ato de vingança "invada"  a discussão paralela e pergunte algo :)

Me interessou sim tinha algumas dúvidas no   flush ();  Obrigado

  • Curtir 1
Link para o comentário
Compartilhar em outros sites

1 minuto atrás, arfneto disse:

Copiei seu programa. Pergunte algo objectivo e vou olhar logo mais

/*
1. Escreva uma função, que insira dados de N funcionários da Universidade Cabo Verde e envia-los para ficheiro como o nome 
funcionarios.txt (o programa deverá informar quantos funcionários deseja inserir no sistema?);
2. Escreva uma função, que imprima registos de todos os funcionários que se encontra no ficheiro com o nome funcionarios.txt, inserido 
anteriormente?
3. Escreva uma função, que imprima os funcionários por categoria. 
4. Escreva uma função, que permite calcular quanto gasta a universidade com os funcionários por categoria? 
5. Temos três tipos de categorias dos funcionários [Docente, Diretor e Técnico], sabendo que o funcionário que é Docente recebe 2500$ 
por cada hora, um Diretor recebe 3500$ por hora, e um Técnico recebe 1500$ por hora. Escreva uma função, que mostra o salário de 
um determinado funcionário dependendo do seu salário liquido por hora, sabendo que INPS é de 12%, IUR é de 20% e sindicato é de 
1%;
6. Escreva uma função, que ordena os funcionários na ordem crescentes e envia-los para o ficheiro com o nome 
ordenar_funcionarios.txt; 
7. Escreva uma função, que imprima todos os funcionários com salario maior que 75000$. 
8. Escreva uma função, que dado nº de NIF permite eliminar todas as informações desse funcionário.  
 */

O objectivo é fazer o programa que é capaz de fazer isso *_*

Link para o comentário
Compartilhar em outros sites

19 minutos atrás, Andrah disse:

O objectivo é fazer o programa que é capaz de fazer isso *_*

 

hey, reproduzir o enunciado não é uma pergunta objetiva.

 

Objetivo é você dizer em que ponto disso tem um problema agora...

 

Algo objetivo:

 

void EliminarFuncionario(struct Funcionario funcionario[], int n);

Esse trecho não está bom

trecho.png.a260febecb11f7662459d4fa6bfef97b.png

 

  • acabou de declarar i. Que acha que vai ter lá?
  • ler um char com o especificador %d é quase certo de cancelar seu programa
  • que 😈 é ativo? Não vi na declaração
  • se não vai fazer nada se file == NULL retorne apenas.
        if (file == NULL)
        {
            printf("\n-->Nao foi possivel abrir o fecheiro\n\n");
            return;
        }
    Pra que deslocar todo o seu programa pra direita? Dificultar a leitura?
     
  • Considere declarar um typedef para struct Funcionario... Para que digitar isso toda hora?
    typedef struct
    {
        char   categoria[20];
        int    Hora_Trabalhados;
        char   nome[20];
        char   NIF[20];
        float  salario;
    }  Funcionario;
    
    // Para não atrapalhar o bom funcionamento
    void menu(Funcionario funcionario[], int n);
  • Essa construção é comum, mas devia ser evitada:

image.png.424c79c293bba862c1b55f39c8d57a6c.png

 

Tudo isso é a mesma coisa. O prompt podia ser um parâmetro de pressioneEnter() não acha? Não seria original, já que o comum. E chamar flush(0 é supérfluo porque pressioneEnter() pode muito bem fazer isso. Limpar a tela e mostrar o menu novamente não sei... Precisaria ver o loop de execução de seu programa...

Algo assim
 

image.png.1c6fa0b8894e219da0e03599b29450ba.png

 

 

adicionado 16 minutos depois

Considere seu programa assim: não mudei nada exceto o mínimo para compilar e aquele if() de que falei

 

Coloquei um parametro em pressioneENTER()

e um int ativo em Funcionario e mudei para um typedef. Mas não mudei nada da lógica. Parece um pouco confuso ainda. Considere as coisas que perguntei. Talvez prefira prosseguir com o programa assim como abaixo. Repito não mudei nada. Mas compila e as funções estão em ordem

 


#include <conio.h>
#include <locale.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>

//Dados do funcionário
typedef struct
{
    int    ativo;
    char   categoria[20];
    int    Hora_Trabalhados;
    char   nome[20];
    char   NIF[20];
    float  salario;
}  Funcionario;

void EliminarFuncionario(Funcionario[], int);
void flush();
void InserirFuncionario(Funcionario[], int);
void menu(Funcionario[], int);
void OrdenarFuncionario(Funcionario*, int);
void pressioneEnter(const char*);


int main()
{
    setlocale(LC_ALL, "Portuguese");
    Funcionario funcionario[100];
    int n = 0;
    Funcionario* p = (Funcionario*) malloc(sizeof(Funcionario));

    if (p == NULL) {
        printf("\n\t ERRO MEMÓRIA INSUFICIENTE!\n");
        exit(1); //Terminar o programa
    }

    system("COLOR F0"); //Abertura do programa
    printf("\n\n\n\n\n\t\t\t....................................................................\n");
    printf("\n\t\t\t\t----> SISTEMA DE REGISTO E CONTROLE DE FUNCIONÁRIO \n");
    printf("\n\t\t\t.....................................................................\n\n\n\n\n");
    printf("\n\t\t\t                                                                      UNICV \n\n");
    printf("\n\tPressione ENTER 2 vezes para iniciar->");
    flush();
    pressioneEnter("");
    system("cls");
    menu(funcionario, n);
    free(p);
    return 0;
};  // main()


void EliminarFuncionario(Funcionario funcionario[], int n) {
    FILE* file;
    //Abre o arquivo novamente para leitura
    file = fopen("funcionarios.txt", "r+");
    if (file == NULL)
    {
        printf("\n-->Nao foi possivel abrir o fecheiro\n\n");
        return;
    }

    int i = 0;
    int nif;
    char resp;
    printf("\n\tInforme o NIF do funcionario a ser Eliminado: ");
    scanf(" %d", &nif);

    //while (funcionario[i].NIF == nif) so para compilar
    while (funcionario[i].NIF[0] == nif)
    {
        if (funcionario[i].ativo == 1)
        {
            printf("\n\tNome: %s", funcionario[i].nome);
            printf("\n\tNIF: %s", funcionario[i].NIF);
            printf("\n\tSalario: %.1f $00", funcionario[i].salario);
            printf("\n\tCategoria: %s", funcionario[i].categoria);
            printf("\n\tHoras de trabalho: %d horas", funcionario[i].Hora_Trabalhados);
            printf("\n\n----------------------------------------------------------\n");
        }

        printf("\n\tDeseja realmente eliminar o Funcionário? S/N:");
        scanf(" %c", &resp);

        if ((resp == 'S') || (resp == 's'))
        {
            funcionario[i].ativo = 0;
            printf("\n\tFuncionário eliminado com sucesso\n");
            break;
        }
        else
        {
            if ((resp == 'N') || (resp == 'n'))
            {
                printf("\tEliminação cancelada!\n");
                break;
            }
        }

        i++;

        if (i > 99)
            printf("\n\n\t\tNIF não encontrado\n");
    };  // while()
    fclose(file);
    pressioneEnter("\n\n\n\t\t\tPressione ENTER para Continuar->");
    system("cls");
};  // EliminarFuncionario()


void flush()
{
    int c;
    /*Lê todos os caracteres até encontrar '\n' ou EOF:*/
    while ((c = getchar()) != '\n' && c != EOF);
};  // flush()


void ImprimirFuncionarios(Funcionario funcionario[], int n) {
    FILE* file;

    file = fopen("C:\\Users\\alex\\Desktop\\ajuda\\funcionarios.txt", "r");

    if (file == NULL)
        printf("\n-->Nao foi possivel abrir o fecheiro\n\n");

    else {
        int i;
        printf("\n\n\n\t\t------- LISTA DOS FUNCIONÁRIOS ------\n\n");

        for (i = 0; i < n; i++) {
            system("COLOR 0F");
            fscanf(file, " %s", funcionario[i].nome);
            fscanf(file, " %s", funcionario[i].NIF);
            fscanf(file, " %f", &funcionario[i].salario);
            fscanf(file, " %s", funcionario[i].categoria);
            fscanf(file, " %d horas", &funcionario[i].Hora_Trabalhados);
            printf("\n\tNome: %s", funcionario[i].nome);
            printf("\n\tNIF: %s", funcionario[i].NIF);
            printf("\n\tSalario: %.1f $00", funcionario[i].salario);
            printf("\n\tCategoria: %s", funcionario[i].categoria);
            printf("\n\tHoras de trabalho: %d horas", funcionario[i].Hora_Trabalhados);
            printf("\n\n----------------------------------------------------------\n");
        }
    }

    pressioneEnter("");
    system("cls");
    fclose(file);
};  // ImprimirFuncionarios()


void InserirFuncionario(Funcionario funcionario[], int n) {
    system("COLOR 0F");
    FILE* file; // cria variável ponteiro para o arquivo
    file = fopen("funcionarios.txt", "w"); //abrindo o arquivo

    if (file == NULL) //testando se o arquivo foi realmente criado
        printf("\n-->Nao foi possivel abrir o fecheiro\n\n");
    else {
        printf("\n\n\n\n\tUNICV \n\n");
        printf("\n\n\n\t\tDigite o numero de Funcionarios que pretende registrar: ");
        scanf(" %i", &n);
        flush();
        system("cls");
        static int i = 0;
        int y = n + i;

        if (y > 99)
            menu(funcionario, n);

        printf("\n\n\n\t\t-------- INSCRIÇÃO DE FUNCIONÁRIO --------\n\n");
        fprintf(file, "\n\n\t----- LISTA DOS FUNCIONÁRIOS ----\n\n");
        fprintf(file, "\tNome      NIF 	  Salário     Categoria    Horas\n\n");

        for (; i < y; i++) {
            system("COLOR 0B");
            // para obter dados e armazenar no arquivo
            printf("\n\tDigite o nome do funcionário: ");
            scanf(" %s", funcionario[i].nome);
            flush();
            printf("\n\tDigite o NIF do funcionário: ");
            scanf(" %s", funcionario[i].NIF);
            printf("\n\tDigite o salario do funcionario: ");
            scanf(" %f", &funcionario[i].salario);
            flush();
            printf("\n\tDigite a categoria do funcionário: ");
            scanf(" %s", funcionario[i].categoria);
            printf("\n\tDigite a Hora trabalhados pelo funcionário: ");
            scanf(" %d", &funcionario[i].Hora_Trabalhados);
            printf("\n\n");
            //A Escrevendo no arquivo
            fprintf(file, "\t%s \t %s \t %.1f \t %s\t %d\n", funcionario[i].nome, funcionario[i].NIF, funcionario[i].salario, funcionario[i].categoria, funcionario[i].Hora_Trabalhados);
        }


        printf("\n\t\t-------------------------<3--------------------------\n");
        printf("\n\t Incritos com sucesso! \n\n\t Registado no fecheiro -> funcionarios.txt\n\n");
        pressioneEnter("\n\n\n\t\t\tPressione ENTER para Continuar->");
        system("cls");
        menu(funcionario, y);
    }

    fclose(file); // para fechar o arquivo
}


void menu(Funcionario funcionario[], int n) {
    int op;
    do {
        system("COLOR 0F"); //Menu
        printf("\n\n\t\t\t\t---> SISTEMA DE REGISTO E CONTROLE DE FUNCIONÁRIO \n\n");
        printf("\n\t\t* 1 ------- INSERIR OS FUNCIONÁRIOS E ENVIA-LOS PARA O FICHEIRO ------------------------ *\n");
        printf("\n\t\t* 2 ------- IMPRIMIR A LISTA DOS FUNCIONÁRIOS DO FICHEIRO ------------------------------ *\n");
        printf("\n\t\t* 3 ------- IMPRIMIR OS FUNCIONÁRIOS POR CATEGORIA ------------------------------------- *\n");
        printf("\n\t\t* 4 ------- GASTO DA UNIVERSIDADE COM OS FUNCIONÁRIOS ---------------------------------- *\n");
        printf("\n\t\t* 5 ------- CALCULAR O SALÁRIO DE UM FUNCIONÁRIO X EM FUNÇÃO DO SEU SALÁRIO POR HORA --- *\n");
        printf("\n\t\t* 6 ------- ORDENAR FUNCIONÁRIO NA ORDEM CRESCENTE ------------------------------------- *\n");
        printf("\n\t\t* 7 ------- IMPRIMIR OS FUNCIONÁRIOS COM SALÁRIO MAIOR QUE 75000$ ---------------------- *\n");
        printf("\n\t\t* 8 ------- ELIMINAR UM FUNCIONÁRIO A PARTIR DO Nº DO NIF ------------------------------ *\n");
        printf("\n\t\t* 0 ------- Sair\n\n");
        printf("\n\tEscolha uma opcao: ");
        scanf(" %d", &op);
        printf("\n");

        switch (op) {
        case 0:
            printf("\t\t\t\t\t\t\t\t\t\t-> Saindo... \n");
            pressioneEnter("\tPressione ENTER para Sair->");
            system("cls");
            break;

        case 1:
            system("cls");
            InserirFuncionario(funcionario, n);
            break;

        case 2:
            system("cls");
            ImprimirFuncionarios(funcionario, n);
            break;

        case 6:
            system("cls");
            OrdenarFuncionario(funcionario, n);
            break;

        case 8:
            system("cls");
            EliminarFuncionario(funcionario, n);
            break;

        default:
            system("COLOR C0");
            printf("\n\t\t\t\t*-*-*-*-- ERRO --> Numero INVALIDO!\n\n");
            printf("\n\tPressione ENTER para Tentar Novamente->");
            flush();
            pressioneEnter("");
            system("cls");
        }
    } while (op != 0);
}


void OrdenarFuncionario(Funcionario* funcionario, int n) {

    int i, j;
    Funcionario aux;

    for (i = 1; i < n; i++) {
        aux = funcionario[i];

        for (j = i; (j > 0) && (aux.salario < funcionario[j - 1].salario); j--) {
            funcionario[j] = funcionario[j - 1];
            funcionario[j] = aux;
        }

    }

    printf("\n\n\n\t------- LISTA DOS FUNCIONÁRIOS POR ORDEM CRESCENTE ------\n\n");

    for (i = 0; i < n; i++) {

        printf("\n\tNome: %s", funcionario[i].nome);
        printf("\n\tNIF: %s", funcionario[i].NIF);
        printf("\n\tSalario: %.1f $00", funcionario[i].salario);
        printf("\n\tCategoria: %s", funcionario[i].categoria);
        printf("\n\tHoras de trabalho: %d horas", funcionario[i].Hora_Trabalhados);
        printf("\n\n----------------------------------------------------------\n");

    }

    printf("\n\n\n\t\t\tPressione ENTER para Continuar->");
    flush();
    pressioneEnter("");
    system("cls");
}


void pressioneEnter(const char* prompt)
{
    char c;
    if(prompt != NULL) printf("%s", prompt);
    do {
        c = getc(stdin);
    } while (c != 13);
};  // pressioneEnter()

// fim

 

  • Curtir 1
  • Obrigado 1
Link para o comentário
Compartilhar em outros sites

1 hora atrás, arfneto disse:

Algo objetivo:

Algo objetivo não sei dizer mas vou tentar resolver os outros e postar aqui se ta algo errado me corrija pode ser?

1 hora atrás, arfneto disse:

O prompt podia ser um parâmetro de pressioneEnter() não acha?

Acho sim Obrigado mesmo :) 

1 hora atrás, arfneto disse:

Repito não mudei nada. Mas compila e as funções estão em ordem

Ta bom Obrigado na mesma! 

Link para o comentário
Compartilhar em outros sites

Neste tipo de programa eu considero que pode haver dois tipos de arquivos onde devem ser escritos dados/informações: Um tipo seria o tipo "relatório" que contém algo para ser lido por um humano, logo deve estar formatado e organizado de forma a facilitar o entendimento pela pessoa que vai ler. O outro tipo seria o tipo "banco de dados" que só será lido pelo programa, logo não há necessidade de formatação pois nenhuma pessoa deve ler este tipo de arquivo diretamente, o que importa para este tipo de arquivo é facilitar que o programa armazene e recupere os dados do arquivo, logo quão mais simples e direto for melhor, e não há necessidade de "embelezar".

 

Digo isso porque tenho perguntas sobre esse enunciado e como você implementou...

 

Veja: Digamos que use o programa 1 vez e cadastre alguns funcionários, se o programa for finalizado quando ele for aberto novamente os funcionários cadastrados anteriormente persistem, ou deve recomeçar a cadastrar do zero toda vez?

 

Acredito que deva recuperar os dados salvos ao abrir o programa, certo?

 

Então isso me diz que o arquivo funcionarios.txt deveria fazer o papel de "banco de dados" e armazenar a lista de funcionários da forma que for mais fácil de acessar e recuperar os dados.

 

 Na função IncerirFuncionario (obs: inserir se escreve com s não com c ) por que você está formatando o texto dentro do arquivo funcionarios.txt?

        fprintf ( file, "\n\n\t----- LISTA DOS FUNCIONÁRIOS ----\n\n" );
        fprintf ( file, "\tNome      NIF 	  Salário     Categoria    Horas\n\n" );

E

            fprintf ( file, "\t%s \t %s \t %.1f \t %s\t %d\n", funcionario[i].nome, funcionario[i].NIF, funcionario[i].salario, funcionario[i].categoria, funcionario[i].Hora_Trabalhados );

 

Ou seja, para que está incluindo os títulos e as tabulações para deixar "bonito" dentro do arquivo? Isso é requisito ou você adicionou por conta própria?

 

Por que se não for requisito isso só vai complicar para recuperar os dados do arquivo para a memória com o fscanf, pois note que primeiro vai ter que ignorar as 2 primeiras linhas, que contém os títulos, para depois começar a ler os dados separados por tabulação.

 

Claro, não é muito difícil fazer isso, mas a questão é se existe a necessidade quando pode fazer algo mais simples que tornaria fazer o código mais fácil e daria mais opções. Por exemplo, poderia separar cada dado do funcionário 1 cada linha (ou seja um '\n' separa cada dado do funcionário), permitindo usar fgets para ler as strings. (Ou até usar o meu método favorito que é, ao invés de fprintf() e fscanf(), usar fwrite() e fread() para escrever e ler do arquivo a struct inteira contendo todos os dados do funcionário de uma vez.)

 

O modo que eu faria esse código (se for usar o método com fprintf e fscanf) a primeira linha do arquivo funcionarios.txt teria a quantidade total de funcionários já armazenadas no arquivo, seguido imediatamente pelos dados de cada funcionário, para facilitar a fazer a função que recupera os dados para a memória na próxima execução do programa.

 

 

Obs: De acordo com a minha distinção de tipos de arquivos o arquivo ordenar_funcionarios.txt poderia ser tanto do tipo "relatório" quanto do tipo "banco de dados", mas como não há nenhuma outra indicação eu usaria como um "relatório" formatando para poder ser lido pelo usuário diretamente.

 

  • Curtir 1
  • Amei 1
Link para o comentário
Compartilhar em outros sites

19 minutos atrás, isrnick disse:

Acredito que deva recuperar os dados salvos ao abrir o programa, certo?

Certo!

19 minutos atrás, isrnick disse:

Na função IncerirFuncionario (obs: inserir se escreve com s não com c ) por que você está formatando o texto dentro do arquivo funcionarios.txt?

Obrigado, para que o usuário possa utilizar o arquivo de pois 

sem precisar escrever tudo de novo 

19 minutos atrás, isrnick disse:

Isso é requisito ou você adicionou por conta própria?

Por conta própria é para deixar mais "bonito" kkkk 

19 minutos atrás, isrnick disse:

(Ou até usar o meu método favorito que é, ao invés de fprintf() e fscanf(), usar fwrite() e fread() para escrever e ler do arquivo a struct inteira contendo todos os dados do funcionário de uma vez.)

Sim poderia fazer assim mas só que o nosso professor não nos encimou e ele não aceita assim porque tem que parecer os dados no arquivo não em binário

tinha feito assim 

/bibliotecas
#include <stdio.h>
#include <stdlib.h>
#include <locale.h>
#include <string.h>
#include <conio.h>
#include <time.h>




//Dados do funcionário
struct Funcionario {
    char nome[20];
    char NIF[20];
    char categoria;
    float salario;
    int diasTrabalhados;
    //Codigo que verifica se o funcionário está ativo no sistema
    int ativo;
};

void pressioneEnter() {
    char c;
    do {
        c = getch();
    } while (c != 13);
}

//Funções a - z
struct Funcionario *criarFuncionario();


void cadastrarFuncionario(struct Funcionario *funcionario, FILE *file) {
    printf("\n-------Cadastro de funcionário--------\n");
    printf("\nInforme o nome do funcionário: ");
    scanf(" %s", funcionario->nome);
    printf("\nInforme o NIF do funcionário: ");
    scanf(" %i", funcionario->NIF);
    printf("\nInforme o salario do funcionario: ");
    scanf("%f", &funcionario->salario);
    printf("\nInforme os dias trabalhados pelo funcionário: ");
    scanf("%d", &funcionario->diasTrabalhados);
    printf("\nInforme a categoria do funcionário: ");
    scanf(" %c", &funcionario->categoria);
    //Ativo no sistema
    funcionario->ativo = 1;
    printf("\nFuncionário inserido com sucesso!");
    fwrite(funcionario, 1, sizeof(struct Funcionario), file);
}

float contarGastos(struct Funcionario *funcionario, FILE *file) {
    float custo = 0;
    while (fread(funcionario, 1, sizeof(struct Funcionario), file)) {
        custo += funcionario->salario;
    }
    return custo;
}

struct Funcionario *criarFuncionario() {
    return (struct Funcionario *)malloc(sizeof(struct Funcionario));
}

void deletarFuncionario(struct Funcionario *funcionario, FILE *file, char *nif) {
    rewind(file);
    while (fread(funcionario, 1, sizeof(struct Funcionario), file)) {
        if (strcmp(funcionario->NIF, nif) == 0 && funcionario->ativo == 1) {
            break;
        }
    }
    fseek(file, -sizeof(struct Funcionario), SEEK_CUR);
    funcionario->ativo = 0;
    fwrite(funcionario, 1, sizeof(struct Funcionario), file);
    printf("\nFuncionario excluido com sucesso!");
}

void listarFuncionarios(struct Funcionario *funcionario, FILE *file) {
    printf("\n------- Listando funcionários ------\n");
    while (fread(funcionario, 1, sizeof(struct Funcionario), file)) {
        if (funcionario->ativo == 1) {
            printf("\nNIF: %s", funcionario->NIF);
            printf("\nNome: %s", funcionario->nome);
            printf("\nCategoria: %c", funcionario->categoria);
            printf("\nSalario: (sua moeda)%.2f", funcionario->salario);
            printf("\nDias trabalhados por semana: %d", funcionario->diasTrabalhados);
            printf("\n----------------------------------------------------------\n");
        }
    }
}

void listarFuncionariosCategoria(struct Funcionario *funcionario, FILE *file) {
    char categoria;
    printf("\nInforme a categoria desejada: ");
    scanf(" %c", &categoria);
    while (fread(funcionario, 1, sizeof(struct Funcionario), file)) {
        if (funcionario->categoria == categoria && funcionario->ativo == 1) {
            printf("\nNIF: %s", funcionario->NIF);
            printf("\nNome: %s", funcionario->nome);
            printf("\nCategoria: %c", funcionario->categoria);
            printf("\nSalario: (sua moeda)%.2f", funcionario->salario);
            printf("\nDias trabalhados por semana: %d", funcionario->diasTrabalhados);
            printf("\n----------------------------------------------------------\n");
        }
    }
}

void menu(struct Funcionario *funcionario) {
    FILE *file;
    int op;
    char nif[20];
    do {
        system("COLOR 0F");  //Menu
        printf("\n\n\n\t\t\t\t---> SISTEMA DE REGISTO E CONTROLE DE FUNCIONARIO \n\n");
        printf("\n\t\t* 1 ------- INSERIR OS FUNCIONARIOS E ENVIA-LOS PARA O FICHEIRO ------------------------ *\n");
        printf("\n\t\t* 2 ------- IMPRIMIR A LISTA DOS FUNCIONARIOS DO FICHEIRO ------------------------------ *\n");
        printf("\n\t\t* 3 ------- IMPRIMIR OS FUNCIONARIOS POR CATEGORIA ------------------------------------- *\n");
        printf("\n\t\t* 4 ------- GASTO DA UNIVERSIDADE COM OS FUNCIONARIOS ---------------------------------- *\n");
        printf("\n\t\t* 5 ------- CALCULAR O SALARIO DE UM FUNCIONARIO X EM FUNCAO DO SEU SALARIO POR HORA --- *\n");
        printf("\n\t\t* 6 ------- ORDENAR FUNCIONARIO NA ORDEM CRESCENTE ------------------------------------- *\n");
        printf("\n\t\t* 7 ------- IMPRIMIR OS FUNCIONARIOS COM SALARIO MAIOR QUE 75000$ ---------------------- *\n");
        printf("\n\t\t* 8 ------- ELIMINAR UM FUNCIONARIO A PARTIR DO N DO NIF ------------------------------- *\n");
        printf("\n\t\t* 0 ------- Sair\n\n\n");
        printf("\n\tEscolha uma opcao: ");
        scanf("%d",&op);
        printf("\n");
        switch (op) {
        case 0:
            printf("\nSaindo...\n");
            break;
        case 1:
            file = fopen("funcionarios.txt", "ab");
            cadastrarFuncionario(funcionario, file);
            fclose(file);
            break;
        case 2:
            file = fopen("funcionarios.txt", "rb");
            listarFuncionarios(funcionario, file);
            break;
        case 3:
            file = fopen("funcionarios.txt", "rb");
            listarFuncionariosCategoria(funcionario, file);
            break;
        case 4:
            file = fopen("funcionarios.txt", "rb");
            printf("\nO total gasto com salarios eh: (sua moeda)%.2f\n", contarGastos(funcionario, file));
            break;
        case 8:
            file = fopen("funcionarios.txt", "rb+");
            printf("\nInforme o NIF do funcionario a ser deletado: ");
            scanf(" %s", nif);
            deletarFuncionario(funcionario, file, nif);
            fclose(file);
            break;
        default:
            system("COLOR C0");
            printf("\n\t\t\t\t*-*-*-*-- ERRO --> Numero INVALIDO!\n\n");
            printf ("\n\tPressione ENTER para Tentar Novamente->");
            fflush(stdin);
            pressioneEnter();
            system("cls");
        }
    } while (op != 0);
}

//Main
int main() {
    setlocale(LC_ALL, "Portuguese");
    system("COLOR F0"); //Abertura do programa
    printf("\n\n\n\n\n\t\t\t....................................................................\n");
    printf("\n\t\t\t\t----> SISTEMA DE REGISTO E CONTROLE DE FUNCIONARIO \n");
    printf("\n\t\t\t.....................................................................\n\n\n\n");
    printf ("\n\tPressione ENTER para iniciar->");
    fflush(stdin);
    pressioneEnter();
    system("cls");
    struct Funcionario *funcionario;
    funcionario = criarFuncionario();
    menu(funcionario);
}

  

  • Curtir 1
Link para o comentário
Compartilhar em outros sites

10 minutos atrás, Andrah disse:

Sim poderia fazer assim mas só que o nosso professor não nos encimou e ele não aceita assim porque tem que parecer os dados no arquivo não em binário

tinha feito assim 

 

Entendi.

Bom, dá pra fazer com fprintf e fscanf. 

 

 

8 minutos atrás, Andrah disse:

Por conta própria é para deixar mais "bonito" kkkk 

 

8 minutos atrás, Andrah disse:

Obrigado, para que o usuário possa utilizar o arquivo de pois 

sem precisar escrever tudo de novo 

 

Não entendi porque o usuário precisaria escrever algo mais de uma vez se não estiver formatado bonitinho.

 

De qualquer maneira se pretende manter assim então tem que corrigir a função ImprimirFuncionarios, pois do modo que está agora ele vai tentar dar fscanf nas 2 linhas com títulos como se fossem dados dos funcionários, e bagunçar toda a leitura, então tem que fazer fscanf ou fgets específico para ler essas 2 linhas que não contém dados.

 

  • Obrigado 1
Link para o comentário
Compartilhar em outros sites

2 minutos atrás, isrnick disse:

De qualquer maneira se pretende manter assim então tem que corrigir a função ImprimirFuncionarios, pois do modo que está agora ele vai tentar dar fscanf nas 2 linhas com títulos como se fossem dados dos funcionários, e bagunçar toda a leitura, então tem que fazer fscanf ou fgets específico para ler essas 2 linhas que não contém dados.

ta bom vou corrigir obrigado 

ta me ajudando muito 

Link para o comentário
Compartilhar em outros sites

1 minuto atrás, arfneto disse:

Você leu o código reordenado? Entendeu as diferenças? O que é o tal campo "ativo"? Viu que eu inseri na estrutura? Vai usar essa estrutura? Entendeu as notas sobre pressioneEnter( e flush()?

sim obrigado mas tem um probleminha 

não ta saindo daqui

Capturar.PNG

Link para o comentário
Compartilhar em outros sites

Agora isto:

        static int i = 0;
        int y = n + i;

        if ( y > 99 )
            menu ( funcionario, n );

E isto:

        menu(funcionario, y);

Dentro da função InserirFuncionario são aberrações que não deveriam existir. 😆

 

Isso está criando recursividade desnecessária e descontrolada, e pior ainda, em ambos os casos chama a função menu sem fechar o arquivo que foi aberto com fopen, aí de dentro do menu pode chamar novamente a função InserirFuncionario, que vai tentar abrir com fopen novamente o arquivo que já está aberto!

 

Mude a lógica para retornar o valor de n seja como retorno da função (muda o tipo da função de void para int), ou então muda a variável n para um ponteiro para que alterações dentro da função também mudem o valor fora dela, ou então faz pedir pra digitar o número de funcionários a serem inseridos fora da InserirFuncionario, na própria menu(), e a InserirFuncionario apenas retornar se teve sucesso ou se falhou (e soma ao total se teve sucesso), em fim tem muitos métodos melhores.

 

  • Obrigado 1
Link para o comentário
Compartilhar em outros sites

3 horas atrás, arfneto disse:
5 horas atrás, vangodp disse:

E você...? Entendeu que funciona também o fgets+sscanf?

 

?

Fico em dúvida se está falando sério. Chamar uma variável local de buffer e usar scanf() para ler dela não mostra nada.

você ta de sacanagem né? Não mostra o que vei...? É que acaso tem que mostrar algo? Funciona, é brilhante pela simplicidade. Por muito que entre o enter este buffer não da erros, é funcional, por muito que que a você não lhe agrade ta aí mais uma forma de ler desde o buffer.
 

4 horas atrás, arfneto disse:

E permite inspecionar o buffer antes de ler.

Mas para que preciso disso??? Ja não viu o 10, não ficou satisfeito???? Que precisa mais?? WTF
 

4 horas atrás, arfneto disse:

Não tem nenhum paralelo com o que está dizendo. Você usa isso na prática quando seu programa está fazendo algo em um loop. Seu programa single-thread, comum. E você precisa ler da entrada. Mas não pode ler da entrada porque vai parar o programa. Então você usa essa função para só ler quando sabe que tem algo. Pense em um game por exemplo.

Do que você ta falando vei??? Que single-thread?? Ralmente n lhe entendo? Faz tempo que conversa ta se distanciando do tema atual.
 

4 horas atrás, arfneto disse:

Ler tudo para uma variável local que você chamou de buffer é folclórico, mas é diferente. Acho que entendeu. Ou não?

Folclórico? você sim ta fazendo um folclore aqui... Para você só o que você posta tem valor, não enxerga outras soluções, somente a sua. E de fato ainda deu uma solução(Queria verlaXD), só se enfoca sobre se eu entendi o que você escreve, e isso que já lhe respondi 500 vezes.
 

 

4 horas atrás, arfneto disse:

Só que você já leu.

E que importa??

 

4 horas atrás, arfneto disse:

Aí vai apontar toda a leitura de seu programa para essa outra variável. Que até tem o nome de buffer. E criou uma nova camada com o mesmo problema.

Não... não tem o mesmo problema... funciona perfeitamente, e você sabe. É uma de tantas mais que existe, toma ou deixa.

 

4 horas atrás, arfneto disse:

E se seu programa for multi-thread então pode ter consumido uma entrada que não era para o particular thread que leu o buffer. E aí vai ter que criar uma nova camada em seu programa para alimentar isso. Pense bem. Está mesmo falando sério ou só me testando...

Vei... vai catar coquinho com os multi-thread. Onde você ta vendo multi-thread aqui? É vontade de causar polêmica n é?
 

4 horas atrás, arfneto disse:

Está mesmo falando sério ou só me testando...

Testando...? Ou testudo?
 

  • Haha 2
Link para o comentário
Compartilhar em outros sites

5 minutos atrás, isrnick disse:

Mude a lógica para retornar o valor de n seja como retorno da função (muda o tipo da função de void para int), ou então muda a variável n para um ponteiro para que alterações dentro da função também mudem o valor fora dela, ou então faz pedir pra digitar o número de funcionários a serem inseridos fora da InserirFuncionario, na própria menu(), e a InserirFuncionario apenas retornar se teve sucesso ou se falhou (e soma ao total se teve sucesso), em fim tem muitos métodos melhores.

Obrigado, vou tentar fazer de outro jeito amanhã e vou postar aqui se tiver alguma coisa errada  me avisa por favor 

  • Curtir 2
Link para o comentário
Compartilhar em outros sites

Arfnet, conforme sua grande experiência... Qual a solução mais adequada ao problema do buffer??? Oh gran arf! Responda só isso. Quero ver... Não! Acho que a essa altura todos queremos ver sua solução perfeita para o tema do LIXO no buffer de entrada. E deixa de baboseiras como consumiu o buffer, multi-thread, e outras mil, que vamos subindo o índice a cada momento.

  • Haha 1
Link para o comentário
Compartilhar em outros sites

O mais interessante seria fazer uma competição para ver quem tem a razão! kkkk

Então quem conseguir fazer o programa como o enunciado pede ( com todos os cases)  ganha!

O que acham kkkkk

Assim todos SAIRIAM FELIZES principalmente EU :) 

Link para o comentário
Compartilhar em outros sites

4 horas atrás, herbertbahia disse:

Haha quanto mais vocês discutem mais eu aprendo. 

Não se vai aprender muito mais sheuhseuh porque o tema vai parar longe ainda ja vai ver shuesueh

adicionado 2 minutos depois
2 minutos atrás, Andrah disse:

O mais interessante seria fazer uma competição para ver quem tem a razão! kkkk

Então ganha o arf... acho que ele sempre tem razão.

 

 

2 minutos atrás, Andrah disse:

Então quem conseguir fazer o programa como o enunciado pede ( com todos os cases)  ganha!

O que acham kkkkk

Assim todos SAIRIAM FELIZES principalmente EU

Claro que conseguimos... Absolutamente todos aqui conseguimos. E você também vai conseguir

  • Curtir 1
  • Triste 1
Link para o comentário
Compartilhar em outros sites

acho que resolver um problema é uma coisa muito boa, mas querer saber qual a melhor solução para  um problema é querer ser o melhor. Creio que com o passar do tempo os sistemas vão mudando ("evoluindo") e muitos desses problemas vão desaparecer. Afinal nem todo mundo é perfeito e os gênios que criaram falharam. Buffer é um assunto complexo e existem diversos tipos.

  • Amei 1
Link para o comentário
Compartilhar em outros sites

1 hora atrás, Andrah disse:

sim obrigado mas tem um probleminha 

não ta saindo daqui

 

Não tentei ler o programa, mas qual a ideia de ENTER 2 VEZES? 

image.png.1a4f002b11a0819089cd783e1402f41a.png

 

Se está tentando isso com uma achamada a pressione ENTER não vai rolar. 

Sua ideia do menu esta confusa sem necessidade. 

Talvez pudesse simplesmente limpar a tela ao entrar no menu uma unica vez.

Ler a opção, tratar, e voltar. Só isso.

 

adicionado 46 minutos depois
1 hora atrás, vangodp disse:

você ta de sacanagem né? Não mostra o que vei...? É que acaso tem que mostrar algo? Funciona, é brilhante pela simplicidade. Por muito que entre o enter este buffer não da erros, é funcional, por muito que que a você não lhe agrade ta aí mais uma forma de ler desde o buffer

 

É estranho dizer que sua própria ideia é brilhante. O "buffer" de que está lendo é uma variável do seu programa. Você já leu do stream e, ao invés de usar fscanf() que leria do buffer do stream, você usa sscanf() que e lê de uma variável do seu programa que você sabiamente chamou de buffer. 

 

image.png.ba3aff31652fc1e3bbaa6d2bb33ac1ec.png

 

1 hora atrás, vangodp disse:

Mas para que preciso disso??? Ja não viu o 10, não ficou satisfeito???? Que precisa mais?? WTF

 

Para que eu preciso disso:

 

Eu te mostrei um exemplo. Mas vou repetir o caso mais simples: imagine que você não quer ler enquanto não tenha nada pra ler. Entenda isso. É importante. Essencial às vezes se seu programa NÃO FOR MULTI-THREAD. 

 

O caso mais simples: seu programa está rodando e é um jogo de console. A tela esta rodando algum tipo de animação. O usuário tem uns comandos, tipo movimento e tiro. E você pode ler os clássicos E S D X para os movimentos e ESPAÇO para atirar. 

 

Se você escrever um fread(), um scanf(), um getc(), um fgets() o programa vai PARAR pra ler o comando até o cara digitar algo. Você só quer ler o comando depois que souber que o cara digitou. Entenda isso. Se não entendeu escreva explicando onde está a dúvida desta vez. É um conceito importante. Você não pode parar a execução e ficar esperando. Também não pode ler para o seu "brilhante" buffer o que ainda não foi digitado. Para isso precisa da colaboração do sistema operacional. No windows pode usar a rotina que te mostrei. No Unix usa algo como ioctl() e faz algo similar. Eu escrevi soluções assim para Unix muitas vezes, mas não me lembro dos detalhes, mas tem algo na estrutura dos buffer do terminal que dava essa informação de que tem algo a ser lido. Sinceramente não me lembro. 

Não adianta nada ler para a sua variável buffer

 

1 hora atrás, vangodp disse:

Não... não tem o mesmo problema... funciona perfeitamente, e você sabe. É uma de tantas mais que existe, toma ou deixa

1 hora atrás, vangodp disse:

E que importa??

 

Espero que tenha entendido agora. São coisas que acontecem em tempo real. Não dá pra ler antes no buffer que está dentro do seu programa porque ninguém digitou ainda. Seu programa segue um loop de execução e se o usuário digitou algo você vai lá e lê. Não pode ler antes de ele ter digitado. Mas às vezes não pode simplesmente escrever um scanf() e ficar esperando...

 

1 hora atrás, vangodp disse:

Vei... vai catar coquinho com os multi-thread. Onde você ta vendo multi-thread aqui? É vontade de causar polêmica n é?

 

Seu tom parece não estar sendo de muita cortesia. Vou explicar isso de novo também: SE FOSSE MULTI-THREAD seu programa poderia ter um loop de execução e outro de leitura e aí o de leitura poderia ficar parado. Entendeu agora? Como o programa, o nosso exemplo aqui,  é um programa comum com uma sequência de execução só, sabe o que acontece se você chama um read: o programa para.

 

1 hora atrás, vangodp disse:

Arfnet, conforme sua grande experiência... Qual a solução mais adequada ao problema do buffer??? Oh gran arf! Responda só isso. Quero ver... Não! Acho que a essa altura todos queremos ver sua solução perfeita para o tema do LIXO no buffer de entrada

 

Talvez possa mudar o tom. Não tenho uma solução perfeita. E já te disse que não se trata de lixo. Não sei se existe tal coisa de solução perfeita. Eu te mostrei as DUAS opções que se usa na prática e até com detalhe: Ler caracteres via getc() ou linhas via gets() e tratar em seu programa. Até citei o que o runtime faz montando o vetor de argv antes de acionar seu programa em C. E quando precisar usar em Windows PeekConsoleInput() para ver se tem algo pra ler e só ler se tiver. E no Linux/Mac ver a outra solução de que falei e não me lembro. E te falei da existência de ungetc() em todas as plataformas. 

 

Já que estou escrevendo, vou te dar um exemplo de que me lembrei agora. Nos '90 eu trabalhava em um sistema grande em UNIX para automação bancária e tinha uma situação em que máquinas especiais eram ligadas como terminais do Unix e o sistema era controlado por dois terminais de uso dos operadores das máquinas. Sempre que a máquina terminava um certo processo uma mensagem indicativa aparecia na tela e o operador tinha que ir até a máquina retirar um lote de documentos e voltar ao terminal para autorizar o reinício. 
 

Durante meses o pessoal pedia uma maneira de escolher um tempo para reinício e voltar sózinho a ler A MENOS que eles usassem algum comando, ao invés de sempre parar e eles terem que voltar ao terminal nem que fosse para teclar um ENTER. Já imaginou o cenário certo? O sistema era escrito em COBOL e minha solução foi escrever um read em C que substituía a leitura do COBOL e depois do tempo que cada operador podia programar em seu turno voltava a acionar as máquinas a menos que o operador digitasse um comando. Entendeu a diferença? Só lia quando ele tinha digitado algo. 

 

1 hora atrás, vangodp disse:

Então ganha o arf... acho que ele sempre tem razão

 

Sinto por isso. Se não entendeu mesmo o que expliquei ou ainda acha que quero criar polêmica. Eu te mostrei vários exemplos. 

 

 

 

Link para o comentário
Compartilhar em outros sites

1 hora atrás, arfneto disse:

Seu tom parece não estar sendo de muita cortesia. Vou explicar isso de novo também: SE FOSSE MULTI-THREAD

Perdoe mas realmente já estou irritado.
Porque aqui não existe MULTI-THREAD, mas você se empenha em por travas.

 

1 hora atrás, arfneto disse:

você sabiamente chamou de buffer. 

E como quer chamar? Conforme wikipedia, definição de buffer é:
Buffer (ciência da computação) - Uma região de memória temporária utilizada para escrita e leitura de dados;


Qual problema há em chama-lo de buffer?

 

1 hora atrás, arfneto disse:

Talvez possa mudar o tom. Não tenho uma solução perfeita.

Mas terá a mais adequada.... e não acredito que seja nem fgets nem getc. Em todos os casos e em todas as soluções o enter vai entrar no buffer. Se eu não posso propor nenhuma solução você também n pode.

você explica as coisas desde um ponto de vista mais tecnico. Talvez dado a que você está acostumado em ver certos tipos de problemas a diário você tenha soluções muito mais "hardcores". Mas o que você não pode fazer é chegar em um post de um estudante iniciante e queimar a cabeça dele com threads etc, isso está fora de contesto, não vai ajudar em nada. Os threads certamente o aluno vai aprender dentro de 3 ou mais anos suheuheus.


Acho que aqui, todos os mais veteranos sabemos que não devemos usar um simples scanf como entrada. Porque se um usuário pode destruir um programa o fará... e vai faze-lo logo de entrada. E se um usuario destruir seu programa, você ainda vai ter que agrader...tipo:
Cliente: O programa fez boom!
Programador: Obrigado por me mostrar que sou um péssimo programador, obrigado por me ensinar que tenho que fazer as coisas direito.XDD

A resposta correta para uma entrada impecável é um conjunto de soluções... especificares, valor de retorno do scanf, validação de dados, etc.

 

1 hora atrás, arfneto disse:

Sinto por isso. Se não entendeu mesmo o que expliquei ou ainda acha que quero criar polêmica. Eu te mostrei vários exemplos. 

Uma coisa é certa... admiro sua paciência.👍 Se você fosse meu professor eu ia te encher o saco o dia todo shuehseuhsuh

 

Eu termino aqui... não vou debater mais nada, porque esse tema já faz tempo que deixou de ser útil para o usuário.

Ainda to esperando o tal exemplo do PeekConsoleInput(). Esse sim me interessa ver.

Obrigado pela paciência e seu tempo.
Em outros tópicos continuaremos com as guerras. sheusheu 👍

Link para o comentário
Compartilhar em outros sites

19 minutos atrás, vangodp disse:

Perdoe mas realmente já estou irritado.
Porque aqui não existe MULTI-THREAD, mas você se empenha em por travas

 

Pois é. Isso é o que estou tentando te explicar: Como não existe isso aqui o programa para no scanf() ou no getc(0 ou no fgets() ou no fread()...

 

Entenda isso: um programa comum para no read. Fica esperando o usu;ario teclar algo.

 

21 minutos atrás, vangodp disse:

E como quer chamar? Conforme wikipedia, definição de buffer é:
Buffer (ciência da computação) - Uma região de memória temporária utilizada para escrita e leitura de dados;


Qual problema há em chama-lo de buffer?

 

Posso chamar as variáveis de meu programa de qualquer coisa, inclusive de buffer, mas isso não vai fazer com que elas sejam um buffer de i/o, de stream como o buffer de teclado ou o de printf() que são controlados pelo sistema operacional e assim criar uma "solução brilhante" para limpar o lixo do buffer do teclado.

23 minutos atrás, vangodp disse:

Em todos os casos e em todas as soluções o enter vai entrar no buffer

 

É o sistema operacional que coloca o ENTER no buffer. E uma leitura no seu programa faz ele parar. Até ter algo no buffer do sistema para ele copiar para a variável buffer do seu programa.

 

24 minutos atrás, vangodp disse:

Mas o que você não pode fazer é chegar em um post de um estudante iniciante e queimar a cabeça dele com threads etc, isso está fora de contesto, não vai ajudar em nada

 

Mas é o contrário o que estou fazendo. Tentado explicar aos leitores o que é um buffer do sistema e uma variável buffer.

E como é vantagem você só ler se sabe se tem algo pra ser lido.

 

Citação

@vangodp Você entendeu o lance de só ler depois de saber que tem algo lá, como num game por exemplo, para não parar o jogo?

 

Exemplo: um jogo de 6 comandos

  • sobe
  • desce 
  • esquerda
  • direita
  • atira
  • encerra

Pergunta:

Como você faz um jogo desses rodar sem parar pra ler o comando?...
 

Resposta:
 

Você roda o jogo e só lê depois do cara ter teclado algo. Assim o read é satisfeito imediatamente e o jogo continua. Sua variável buffer, com ou sem o ENTER, de nada serviria.

 

31 minutos atrás, vangodp disse:

Uma coisa é certa... admiro sua paciência.👍 Se você fosse meu professor eu ia te encher o saco o dia todo

 

:) por sorte você não tem o dia todo.

 

Não vou julgar se eu tenho paciência ou me julgar de qualquer modo. Mas meu pessoal diz isso às vezes.

 

32 minutos atrás, vangodp disse:

Ainda to esperando o tal exemplo do PeekConsoleInput(). Esse sim me interessa ver.

 

Vou separar algo antigo que dê pra usar em "slides" e postar aqui qualquer hora

Link para o comentário
Compartilhar em outros sites

Crie uma conta ou entre para comentar

Você precisa ser um usuário para fazer um comentário

Criar uma conta

Crie uma nova conta em nossa comunidade. É fácil!

Crie uma nova conta

Entrar

Já tem uma conta? Faça o login.

Entrar agora

Sobre o Clube do Hardware

No ar desde 1996, o Clube do Hardware é uma das maiores, mais antigas e mais respeitadas comunidades sobre tecnologia do Brasil. Leia mais

Direitos autorais

Não permitimos a cópia ou reprodução do conteúdo do nosso site, fórum, newsletters e redes sociais, mesmo citando-se a fonte. Leia mais

×
×
  • Criar novo...

Ebook grátis: Aprenda a ler resistores e capacitores!

EBOOK GRÁTIS!

CLIQUE AQUI E BAIXE AGORA MESMO!