#include <iostream>
#include <cmath>

#define MIN3(A, B, C) std::min(A, std::min(B, C))

typedef double value_type;

using std::cout;
using std::endl;
using std::sqrt;

struct RGB
{
    value_type R, G, B;
};

struct HSI
{
    value_type H, S, I;
};

void convertRGBtoHSI(RGB input, HSI &output)
{
    RGB &color = input;
    value_type &hue = output.H;
    value_type &saturation = output.S;
    value_type &intensity = output.I;

    intensity = (color.R + color.G + color.B) / 3;

    if((color.R + color.G + color.B) == 765)
    {
        saturation = 0;
        hue = 0;
    }

    MIN3(color.R, color.G, color.B);
    if(intensity > 0)
    {
        value_type did = MIN3(color.R, color.G, color.B)/ intensity;
        saturation = 1 - did;
    }
    else if (intensity == 0)
    {
        saturation = 0;
    }
    value_type color123 = (color.R * color.R) + (color.G * color.G) +
            (color.B * color.B) - (color.R * color.G) -
            (color.R * color.B) - (color.G * color.B);
    double sqrt2 = (double)sqrt((double)color123);
    value_type temp = (color.R - (color.G/2) - (color.B/2)) / ( sqrt2 );
    if (color.G >= color.B)
    {
        hue = acos(temp);
    }
    else if (color.B > color.G)
    {
        hue = 360 - acos(temp);
    }
}


int main()
{
    RGB a = {255, 255, 255};
    HSI b;
    convertRGBtoHSI(a, b);
    
    cout << "Input  : " << a.R << ", " << a.G << ", " << a.B << endl;
    cout << "Output : " << b.H << ", " << b.S << ", " << b.I << endl;

    return 0;
}