#include <iostream>
#include <climits>
#include <cassert>

struct Punkt
{
  double          X, Y;
};

struct WezelStosu
{
  Punkt           P;
  WezelStosu     *Nastepny;
};

struct Stos
{
  WezelStosu     *Pierwszy;
};

Punkt 
Pkt(double X, double Y)
{
  Punkt           P;
  P.X = X;
  P.Y = Y;
  return (P);
}

void 
Init(Stos & S)
{
  S.Pierwszy = 0;
}

void 
Push(Stos & S, const Punkt & P)
{
  WezelStosu     *nowy = new WezelStosu;
  nowy->P = P;
  nowy->Nastepny = S.Pierwszy;
  S.Pierwszy = nowy;
}

void 
Push(Stos & S, double X, double Y)
{
  WezelStosu     *nowy = new WezelStosu;
  nowy->P.X = X;
  nowy->P.Y = Y;
  nowy->Nastepny = S.Pierwszy;
  S.Pierwszy = nowy;
}

bool 
IsEmpty(const Stos & S)
{
  return (!S.Pierwszy);
}

Punkt 
Pop(Stos & S)
{
  assert(S.Pierwszy);
  //jezeli S.Pierwszy == 0 to koniec programu z odpowiednim komunikatem
    WezelStosu * stary = S.Pierwszy;
  S.Pierwszy = stary->Nastepny;
  Punkt           Wynik = stary->P;
  delete          stary;
  return (Wynik);
}

void 
Clear(Stos & S)
{
  while (S.Pierwszy)
  {
    WezelStosu     *stary = S.Pierwszy;
    S.Pierwszy = stary->Nastepny;
    delete          stary;
  }
}

void 
Print(const Punkt & P)
{
  cout << '(' << P.X << ',' << P.Y << ')';
}

void 
Print(const Stos & S)
{
  for (WezelStosu * i = S.Pierwszy; i; i = i->Nastepny)
  {
    Print(i->P);
    cout << endl;
  }
}

int 
main()
{
  Stos            S;
  Init(S);
  Punkt           PP = {11, 11};
  Push(S, PP);
  Push(S, Pkt(22, 22));
  Push(S, 33, 33);
  while (!IsEmpty(S))
  {
    cout << endl;
    Print(S);
    Punkt           P = Pop(S);
    cout << "Pobrany punkt: ";
    Print(P);
    cout << endl;
  }
  Clear(S);
  cout << "Stos jest pusty. Proba pobrania ...";
  cin.ignore(INT_MAX, '\n');
  Pop(S);

  return 0;
}

