Skip to content

Instantly share code, notes, and snippets.

@Warwolt
Created February 4, 2020 16:11
Show Gist options
  • Save Warwolt/df9febd79d74cd0ff9f4aa1c09837f45 to your computer and use it in GitHub Desktop.
Save Warwolt/df9febd79d74cd0ff9f4aa1c09837f45 to your computer and use it in GitHub Desktop.
#include <stdio.h>
#include <stdlib.h>
enum result_type {OK, ERROR};
#define _RESULT_TYPE_NAME(a, b) _ ## a ## _ ## b ## _result
#define RESULT_TYPE_NAME(a, b) _RESULT_TYPE_NAME(a, b)
#define RESULT_TYPE(ret_type, err_type) struct RESULT_TYPE_NAME(ret_type, err_type)
#define DEFINE_RESULT_TYPE(ret_type, err_type) \
RESULT_TYPE(ret_type, err_type) \
{ \
enum result_type type; \
union \
{ \
struct { ret_type value; }; \
struct { err_type error; }; \
}; \
}
typedef enum {FIRST_OPERAND_NEGATIVE, SECOND_OPERAND_NEGATIVE, BOTH_OPERANDS_NEGATIVE} errnum_t;
DEFINE_RESULT_TYPE(int, errnum_t);
RESULT_TYPE(int, errnum_t) add_natural_nums(int a, int b)
{
RESULT_TYPE(int, errnum_t) result;
if (a < 0 || b < 0)
{
result.type = ERROR;
result.error = BOTH_OPERANDS_NEGATIVE;
return result;
}
if (a < 0)
{
result.type = ERROR;
result.error = FIRST_OPERAND_NEGATIVE;
return result;
}
if (b < 0)
{
result.type = ERROR;
result.error = SECOND_OPERAND_NEGATIVE;
return result;
}
result.type = OK;
result.value = a + b;
return result;
}
int main(int argc, char **argv)
{
/* Check args */
if (argc < 3)
{
printf("usage: %s num1 num2\n", argv[0]);
return 1;
}
/* Calculate sum */
int a = atoi(argv[1]);
int b = atoi(argv[2]);
RESULT_TYPE(int, errnum_t) result = add_natural_nums(a, b);
/* Check result */
if (result.type == ERROR)
{
if (result.error == BOTH_OPERANDS_NEGATIVE)
{
printf("error: both operands %d and %d were negative!\n", a, b);
}
if (result.error == FIRST_OPERAND_NEGATIVE)
{
printf("error: first operand %d was negative!\n", a);
}
if (result.error == SECOND_OPERAND_NEGATIVE)
{
printf("error: second operand %d was negative!\n", b);
}
}
else if (result.type == OK)
{
printf("%d + %d = %d\n", a, b, result.value);
}
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment