Commit 36723b6f authored by Dominik Widhalm's avatar Dominik Widhalm
Browse files

Added example solutions for task 6.11

parent 26531941
/******************************************************************************
* C PROGRAMMING *
* BASIC EXERCISES - EXAMPLE SOLUTIONS *
* *
* Task_6.11: Universal Data Acquisition *
* Author: Dominik Widhalm *
* Email: dominik.widhalm@technikum-wien.at *
* Date: 2017-08-31 *
* *
******************************************************************************/
/***** INCLUDES ***************************************************************/
#include <stdio.h>
#include <time.h>
#include <stdlib.h>
#include <string.h>
/***** MACROS *****************************************************************/
// Maximum length of strings
#define STRING_MAX 20
/***** TYPEDEFS ***************************************************************/
/* Enumeration type for value type */
typedef enum {INTEGER, FPOINT} type_t;
/* Enumeration type for analyze return value */
typedef enum {VALID, INVALID} retval_t;
/* Struct type for the universal value */
typedef struct data {
// Enumeration for the contained value type
type_t type;
// Union for the actual value
union value {
// Integer
int d;
// Double
double f;
} value;
} data_t;
/***** FUNCTION PROTOTYPES ****************************************************/
retval_t analyze_input (char *input, data_t *space);
/***** LOCAL FUNCTIONS ********************************************************/
/******************************************************************************
* analyze_input *
* @brief Function to analyze a given string for a valid number. *
* *
* This function iterates over the given string and checks if it *
* contains a valid int or double value (double separated by '.'). If a *
* valid number was found it is stored on the given address. *
* *
* @param input Pointer to the input string *
* @param space Pointer to the memory location *
* @retval VALID Valid number was found *
* @retval INVALID No valid number was found *
******************************************************************************/
retval_t analyze_input (char *input, data_t *space) {
/* Flag if a dot was found */
int dot = 0;
/* Index of position after the dot */
int index = 1, divisor = 0;
/* Temporary value */
double temp = 0.0;
/* First check if string does not start with a digit */
if ((*input < '0') || (*input > '9')) {
/* Invalid input */
return INVALID;
}
/* Iterate over the given string */
while (*input != '\0') {
/* Check if the current character is a digit */
if ((*input >= '0') && (*input <= '9')) {
/* Check if a dot has already been found */
if (dot == 1) {
/* Calculate current divisor */
divisor=1;
for (int i=0; i<index; i++) {
divisor *= 10;
}
/* Add value behind the dot */
temp += ((double)(*input-'0') / (double)divisor);
/* Increment position after dot */
index++;
} else {
/* Shift previous number */
temp *= 10;
/* Value before the dot */
temp += (*input-'0');
}
/* Check if the current character is a dot */
} else if (*input == '.') {
/* Check if a dot has already been found */
if (dot == 1) {
/* Invalid input */
return INVALID;
} else {
/* Set dot has been found */
dot = 1;
}
/* Otherwise ... */
} else {
/* ... the input is invalid */
return INVALID;
}
/* Go to the next character */
input++;
}
/* Check if value is double (dot was found) */
if (dot == 1) {
/* Value type is FPOINT */
space->type = FPOINT;
/* Store the extracted value */
space->value.f = temp;
} else {
/* Value type is INTEGER */
space->type = INTEGER;
/* Store the extracted value */
space->value.d = (int)temp;
}
/* A valid input was found */
return VALID;
}
/***** MAIN ROUTINE ***********************************************************/
int main (void) {
/*** Local Variables ***/
data_t *values;
data_t *curr;
int count;
double sum = 0.0;
/* Initialize the random function with the current system time */
srand((unsigned int)time(NULL));
/* Get a random number */
count = rand()%20 + 1;
/* Allocate the required amount of memory */
values = (data_t*)malloc(count*sizeof(data_t));
/* Check if memory could be allocated */
if (values != NULL) {
/* Inform the user how many number inputs are expected */
printf("\nIn the following %d numbers will be processed ...\n",count);
/* Read in the desired number of values */
curr = values;
for (int i=0; i<count; i++) {
/* Input validity flag */
int valid = 0;
/* Temporary string for user input */
char temp[STRING_MAX];
/* Do at least one input */
do {
/* Ask the user to input the number */
printf(" ... please enter the %d. value: ",(i+1));
/* Read in the user's input */
scanf("%s",temp);
/* Analyze the given string */
if (analyze_input(temp,curr) == VALID) {
/* Valid input */
valid = 1;
} else {
/* Invalid input */
printf("... invalid input!\n");
}
/* Repeat until valid number was entered */
} while (valid == 0);
/* Go to the next number */
curr++;
}
/* Iterate over all values */
curr = values;
for (int i=0; i<count; i++) {
/* Check if current value is INTEGER */
if (curr->type == INTEGER) {
/* Add value to the sum */
sum += (double)curr->value.d;
/* ... current value is FPOINT */
} else {
/* Subtract value from the sum */
sum -= curr->value.f;
}
/* Go to the next number */
curr++;
}
/* Print the calculated result */
printf("\nThe result of the performed calculation is %.2f\n\n",sum);
/* Free the allocated memory */
free(values);
} else {
/* Could not allocate memory */
printf("\nERROR: could not allocate memory!\n\n");
}
/* Notify the user about the termination of the program */
printf("The program will now be terminated...\n");
return 0; /* Return with Success (0) */
}
/******************************************************************************/
# Get the current path(s) (relevant directory on last position)
TASKPATH := $(dir $(abspath $(lastword $(MAKEFILE_LIST))))
CHPATH := $(dir $(TASKPATH:%/=%))
# Variables for text substitution
empty:=
slash:= /
space:= $(empty) $(empty)
task:= task_
ch:= ch_
# Get TASK number
TASK := $(subst $(slash),$(space),$(TASKPATH))
TASK := $(lastword $(TASK))
TASK := $(subst $(task),$(empty),$(TASK))
# Get CH number
CH := $(subst $(slash),$(space),$(CHPATH))
CH := $(lastword $(CH))
CH := $(subst $(ch),$(empty),$(CH))
# Specify SRD directory
SRCDIR = .
# Call superior makefile
include ../../makefile
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment