/*
                                Denise-MYTH Artificial Intelligence.

                                  Copyright (C) 2000 Szymon Jessa

                                         WERSJA ANGIELSKA:

This  program  is free software; you can redistribute it and/or modify it under the terms of the GNU
General  Public  License  as  published  by  the  Free  Software Foundation; either version 2 of the
License, or (at your option) any later version.

This  program  is  distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without
even  the  implied  warranty  of  MERCHANTABILITY  or  FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.

You  should  have received a copy of the GNU General Public License along with this program; if not,
write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.

                                           WERSJA POLSKA:

Niniejszy   program   jest  oprogramowaniem  wolnodostëpnym;  moûesz  go  rozprowadzaê  dalej  i/lub
modyfikowaê na warunkach Powszechnej Licencji Publicznej GNU, wydanej przez Fundacjë Wolnodostëpnego
Oprogramowania - wedîug wersji 2-giej tej Licencji lub którejô z póúniejszych wersji.

Niniejszy   program  rozpowszechniany  jest  z  nadziejâ,  iû  bëdzie  on  uûyteczny  -  jednak  BEZ
JAKIEJKOLWIEK  GWARANCJI,  nawet  domyôlnej  gwarancji  PRZYDATNOÔCI  HANDLOWEJ albo PRZYDATNOÔCI DO
OKREÔLONYCH ZASTOSOWAÏ. W celu uzyskania bliûszych informacji - Powszechna Licencja Publiczna GNU.

Z  pewnoôciâ  wraz  z niniejszym programem otrzymaîeô teû egzemplarz Powszechnej Licencji Publicznej
GNU; jeôli nie - napisz do Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.

                                              KONTAKT:

snail: Szymon Jessa, ul. Warszawska 20/6, 89-600 Chojnice,
email: smoczek@ue.eti.pg.gda.pl (ew. noco@box43.gnet.pl)
phone: (052) 39-707-88

****************************************************************************************************
*/
/*
	funkcje odpowiedzialne za odpowiadanie na pytania szczegóîowe, ogólne, podmiotwe
*/

char FROM ans_ogolne(struct fakt_struct *fakt)
{
   /*
   ZASADA GÎÓWNA PYTANIA OGÓLNEGO:
   pytanie ogólne wystëpuje wtedy, gdy w zdaniu jest zaimek pytajâcy ale nie podmiotowy!

	algorytm odpowiadania na pytanie:
	- tworzy sië listë fp, które speîniajâ warunki odpowiedzi na zadane pytanie,
     tj. sâ nie zaimkowâ czëôciâ mowy okreôlonâ przez zaimek,
     przy zachowaniu okreôlonych przez zaimek parametrów (tj. odmiany)
	- wybiera sië jeden fp jako odpowiedú i wypisuje na ekranie po odmienieniu

	UWAGA! przy nadmiarze fp wykonywane sâ operacji selekcji, dokîadnie tak
	jak w przypadku zadawania pytania (patrz quest1.c)

   WYBÓR FP:
	- wspóîczynnik inteligencji:
		- stopieï zgodnoôci grup (patrz ans_quality)
		- ?
	- wspóîczynnik intuicji:
		- droga losowa
	*/

	char ile_odp=0,odp_nr,quality_table=0,txt[MAX_LINE_LENGHT],quality,depth;
	struct obiekt_struct *obiekt;
	struct simple_struct *simple;
	struct fp_table_struct fp_table[MAX_INTELLIGENCE_TABLE];

	for (obiekt=fakt->obiekt_head;obiekt!=NULL;obiekt=obiekt->next)
	{
		for (simple=obiekt->funkc_head;simple!=NULL;simple=simple->next)
		{
         // jeôli to pytanie ogólne, to aby znaê na nie odpowiedú musimy
         // mieê fp co najmniej taki sam dîugi jak pytanie
         if (rozbior.obiekt->funkc_head->ile_grup>simple->ile_grup) continue;

			// * * * INTELIGENCJA * * *
			// jeôli wartoôê odpowiedzi jest mniejsza od ustalonej inteligencji
			// to nie akceptujemy jej, ale w przypadku, gdy lista odpowiedzi jest
			// pusta, to zawsze dopisujemy odpowiedzi najwyûej ocenione,
			// zastëpujâc nimi gorsze
			quality=ans_quality(obiekt,simple);

         // jeôli quality==0 to tak czy inaczej pomijamy të odpowiedú
         if (quality==0) continue;

			// jeôli do tej pory max_quality byîo <intelligence, a teraz
			// jest quality>=intelligence, to zerujemy tablicë
			if (quality>=intelligence && quality_table<intelligence) ile_odp=0;

			// jeôli to pierwsza odpowiedú na liôcie to dopisujemy tak czy inaczej
			// a jeôli jest lista, to zaleûy, od wartoôci max_quality
			if (quality<intelligence && ile_odp>0)
			{
				// jeôli jakoôê odpowiedzi jest mniejsza od aktualnych na liôcie
				if (quality<quality_table) continue;
				// jeôli jest wiëksza, to kasujemy listë
				else if (quality>quality_table)
				{
					ile_odp=0;
				}
				// jeôli jest tej samej jakoôci, to dopisujemy dalej
			}

			if (ile_odp==0) quality_table=quality;

			// jeôli tablica jest peîna, to losowo nadpisujemy, lub nie
			if (ile_odp==MAX_INTELLIGENCE_TABLE)
			{
				if ((drand() % 2)==0) continue; // to nie dopisujemy
				// w przeciwnym razie dopisujemy pod jakimô losowym numerem
				odp_nr=drand() % MAX_INTELLIGENCE_TABLE;
			}
			else
			{
				(ile_odp)++;
				odp_nr=ile_odp-1;
			}

			fp_table[odp_nr].obiekt=obiekt;
			fp_table[odp_nr].simple=simple;
		}
	}
	if (view.odpowiedz==KOD_TRUE)
	{
		// rezultat sita inteligencji
		sprintf(txt,"sito inteligencji: (fpf) %d z %d (%d%%)\n",ile_odp,fakty_count_simple(MODE_FPF,fakt,NULL),quality_table);
		con_put(txt);
	}

	// jeôli nie moûna utworzyê pytania to BRAK DANYCH (ale wszystko w porzâdku)
	if (ile_odp==0)
   {
      con_put_komunikat(E_DENISE_PYTANIE_BRAK_DANYCH);
      return RESULT_OK;
   }

	// * * * INTUICJA * * *
	// losowanie odpowiedzi z listy
	odp_nr=drand() % ile_odp; // odpowiedú od 0 do (ile_odp-1)

	if (view.odpowiedz==KOD_TRUE)
	{
		// rezultat sita intuicji
		sprintf(txt,"sito intuicji: nr %d z %d\n",odp_nr+1,ile_odp);
		con_put(txt);
	}

	// ostateczne dobranie gîëbokoôci odpowiedzi
	// (nie moûe byê dîuûsza niû w bazie, ale moûe byê dîuûsza niû pytanie)
	depth=min(rozbior.obiekt->funkc_head->ile_grup,fp_table[odp_nr].simple->ile_grup);
	if (depth<fp_table[odp_nr].simple->ile_grup)
	{
		if (view.odpowiedz==KOD_TRUE) con_put("intuicja: losowe dobranie gîëbokoôci pytania\n");
		depth=depth+ (drand() % (fp_table[odp_nr].simple->ile_grup-rozbior.obiekt->funkc_head->ile_grup+1));
	}

	// wypisanie odpowiedzi o dobranej gîëbokoôci
	ans_ogolne_show(fp_table[odp_nr].obiekt,fp_table[odp_nr].simple,depth);

	return RESULT_OK;
}

void FROM ans_ogolne_show(struct obiekt_struct *obiekt,struct simple_struct *simple,char depth)
{
	char nr1;
	static struct odmiana_struct zdanie; // dlaczego do jasnej ma byê static!

	// odmiana

	// wpisanie danych o grupach
	for (nr1=0;nr1<depth;nr1++)
	{
		// grupa podstawowa
		if (fgrupa_get_body(obiekt->podstawowe,simple->opis[nr1],zdanie.podst[nr1])==RESULT_NO_OK) con_put("bîâd: kubuô 1 totalfatalista!\n");
		// funkcja, poziom, wyraz nadrzëdny
		zdanie.funkcja[nr1]=obiekt->funkcja[simple->opis[nr1]];
		zdanie.poziom[nr1]=nr1;
		zdanie.zwiazek[nr1]=nr1-1;
	}
	zdanie.ile_grup=depth;

   // wpisanie charakterystyki zdania
   zdanie.typ_podmiotu=rozbior.typ_podmiotu;
	zdanie.podmiot_ident=rozbior.podmiot_ident;
	zdanie.podmiot=0;
	zdanie.orzeczenie=1;
   zdanie.twierdz_przecz=ZDANIE_TWIERDZACE;
   zdanie.oznajm_pyt=ZDANIE_OZNAJMUJACE;

	// wpisanie danych pomocniczych (skoro je posiadamy, to sië nimi dzielimy ;))
   zdanie.fakt=NULL;
   zdanie.obiekt=obiekt;
   zdanie.simple=simple;

   odmiana_main(&zdanie);

	// koniec odmiany
   short_info.output=DENISE_OUTPUT;
   con_put_dialog(PODMIOT_DENISE,zdanie.wynik,PRIORITY_ANS_ZG);
}

// * * * funkcje oceny wartoôci odpowiedzi ogólnej * * *

char FROM ans_quality(struct obiekt_struct *obiekt,struct simple_struct *simple)
{
	/*
	obiekt/simple - fakt prosty simple z obiekt, jako odpowiedú do rozbioru

	UWAGA! ocena dotyczy tylko jednego faktu prostego rozbioru!!!

	o jakoôci odpowiedzi decyduje stopieï zgodnoôci z pytaniem:
	- zgodnoôê poszczególnych grup faktów prostych:
		- funkcja w zdaniu
		- wyraz podstawowy
		- czëôê mowy
	- w przypadku grupy zaimkowej:
		- funkcja w zdaniu
		- toûsamoôê czëôci mowy
		- dla zaimka rzeczownego kontrola OSOBOWOÔCI

   UWAGA! wymagana jest 100% zgodnoôê dwóch pierwszych grup, tj. podmiotu i orzeczenia!
   UWAGA! wymagana jest zgodnoôê zaimka z wyrazem toûsamym, tj. jeôli zaimek
          jest ZAIMKIEM LICZEBNYM to jedynâ akceptowalnâ odpowiedziâ jest LICZEBNIK
	*/

	int quality=0,max_quality=0;
   char nr1,nr2,nra,nrb,podsta[MAX_LINE_LENGHT];
	char max_ile_grup=min(rozbior.obiekt->funkc_head->ile_grup,simple->ile_grup);
	static char podstb[MAX_LINE_LENGHT];
	struct fleksja_struct *word;

   char txt[MAX_LINE_LENGHT];

	// nra - numer grupy w rozbiorze zgodnie z kolejnoôciâ grup w rozbior
	// nrb - numer grupy w obiekcie zgodnie z kolejnoôciâ grup w simple->opis

	for (nr1=0;nr1<max_ile_grup;nr1++)
	{
      if (view.odpowiedz==KOD_TRUE && nr1>0)
      {
         sprintf(txt,"%s == %s - quality: %d\n",podsta,podstb,100*quality/max_quality);
         con_put(txt);
      }

      // jeôli to dwie pierwsze grupy to wymagana jest 100% zgodnoôê!
      if (nr1>0 && nr1<=2 && quality<max_quality)
      {
         if (view.odpowiedz==KOD_TRUE && nr1>0)
         {
            sprintf(txt,"zbyt niska jakoôê odpowiedzi\n");
            con_put(txt);
         }
         return (char) 0;
      }

		// * pobranie wstëpnych danych
		// numery grup
		nra=rozbior.obiekt->funkc_head->opis[nr1];
		nrb=simple->opis[nr1];

		// wyrazy podstawowe
		for (sprintf(podsta,""),nr2=0;nr2<rozbior.grupa[nra].ile_wyrazow;nr2++)
		{
			strcat(podsta,rozbior.podst[rozbior.grupa[nra].wyraz[nr2]]);
			if (nr2<rozbior.grupa[nra].ile_wyrazow-1) strcat(podsta," ");
		}
		fgrupa_get_body(obiekt->podstawowe,nrb,podstb);

		// * okreôlenie QUALITY
		// porównanie funkcji grup w zdaniu
		max_quality+=1+2*(max_ile_grup+1)/(nr1+1);
		if (rozbior.funkcja[nra]==obiekt->funkcja[nrb] ||
          (rozbior.funkcja[nra]==ORZECZENIE_CZASOWNIKOWE && obiekt->funkcja[nrb]==LACZNIK) ||
          (rozbior.funkcja[nra]==LACZNIK && obiekt->funkcja[nrb]==ORZECZENIE_CZASOWNIKOWE)) quality+=1+2*(max_ile_grup+1)/(nr1+1);

		// porównanie wyrazów podstawowych grup
		max_quality+=1+2*(max_ile_grup+1)/(nr1+1);
		if (strcmp(podsta,podstb)==0) quality+=1+2*(max_ile_grup+1)/(nr1+1);

		// PARAGRAF TOÛSAMOÔCI Z ZAIMKIEM
		word=fleksja_find("",podstb,NULL,FULL);
		// konieczna jest znajomoôê czëôci mowy badanej grupy
		// UWAGA! nie sâ obsîugiwane grupy wielowyrazowe!!! *7*
		if (word==NULL) continue;

		// zgodnoôê czëôci mowy (jeôli nie jest zgodny ZAIMEK to quality=0)
		switch (*ptr_czesc_mowy(rozbior.dane[nra]))
		{
			case ZAIMEK_RZECZOWNY:
				max_quality+=4;
				if (*ptr_czesc_mowy(word->klon_head->dane)==RZECZOWNIK)
				{
					quality+=2;
					// kontrola OSOBOWOÔCI
					if (*ptr_osobowosc(word->klon_head->dane)==*ptr_osobowosc(rozbior.dane[nra])) quality+=2;
               else return (char) 0;
				}
				break;
			case ZAIMEK_PRZYMIOTNY:
				max_quality+=2;
				if (*ptr_czesc_mowy(word->klon_head->dane)==PRZYMIOTNIK) quality+=2;
            else return (char) 0;
				break;
			case ZAIMEK_PRZYSLOWNY:
				max_quality+=2;
				if (*ptr_czesc_mowy(word->klon_head->dane)==PRZYSLOWEK) quality+=2;
            else return (char) 0;
				break;
			case ZAIMEK_LICZEBNY:
				max_quality+=2;
				if (*ptr_czesc_mowy(word->klon_head->dane)==LICZEBNIK) quality+=2;
            else return (char) 0;
   			break;
		}
   }

   if (view.odpowiedz==KOD_TRUE && nr1>0)
   {
      sprintf(txt,"%s == %s - quality: %d\n\n",podsta,podstb,100*quality/max_quality);
      con_put(txt);
   }

	return (char) (100*quality/max_quality);
}

// * * * odpowiedú na pytanie podmiotowe * * *

char FROM ans_podmiotowe(void)
{
   /*
   pytanie podmiotowe - pytanie o rdzeï/podmiot, np.:
   KTO jest czîowiekiem?
   CO stoi na parkingu?
NIE ZROBIONE:    KTO ma ucznia? -> JEÔLI: darek jest uczniem andrzeja ODPOWIEDZ: ANDRZEJ

   algorytm:
   - tworzenie listy faktów zgodnych z pytaniem
     (tj. o rdzeniu, który speînia dalszâ czëôê zdania)
     UWAGA! jest kontrola OSOBOWOÔCI!
     UWAGA! wykorzystywane jest WNIOSKOWANIE DZIEDZICZONE!
     UWAGA! NIE JEST wykorzystywane WNIOSKOWANIE PRZYDAWKOWE!
     UWAGA! kaûda odpowiedú jest oceniana - czynnik INTELIGENCJI
   - intuicyjne wybranie jednego z faktów z tablicy - czynnik INTUICJI
   - wyôwietlenie odpowiedzi (samego rdzenia lub peînego zdania)

   UWAGA! kontrola dla odpowiedzi typu: "chîopak jest chîopakiem":
   - jeôli jest orzecznik, to rdzeï faktu odpowiedzi musi byê od niego róûny!
   */

   struct fakt_struct *mother,*fakty_table[MAX_INTELLIGENCE_TABLE];
   struct fleksja_struct *word;
   char ile_odp=0,odp_nr,txt[MAX_LINE_LENGHT],quality,quality_table=0,nr1;
   char podst[MAX_LINE_LENGHT],odm[MAX_LINE_LENGHT];

   // sprawdzamy wszystkie fakty z bazy
   for (mother=fakt_head;mother!=NULL;mother=mother->next) 
   {
      // pobieramy rdzeï mother-faktu
      if (fgrupa_get_body(mother->obiekt_head->podstawowe,mother->obiekt_head->ident_head->opis[0],podst)==RESULT_NO_OK) continue;
      if (fgrupa_get_body(mother->obiekt_head->odmienione,mother->obiekt_head->ident_head->opis[0],odm)==RESULT_NO_OK) continue;
      if ((word=fleksja_find(odm,podst,NULL,FULL))==NULL) continue;

      // jeôli jest orzecznik w pytaniu to rdzeï musi byê od niego róûny
      for (nr1=0;nr1<rozbior.ile_grup;nr1++)
      {
         if (rozbior.funkcja[nr1]==ORZECZNIK)
         {
            if (strcmp(word->podst,rozbior.podst[nr1])==0) goto NEXT_MOTHER_FAKT;
         }
      }

      // kontrola osobowoôci
      if (*ptr_osobowosc(word->klon_head->dane)!=*ptr_osobowosc(rozbior.dane[rozbior.podmiot])) continue;

      // jeôli mother zawiera fakt pytania w sobie, to dopisujemy do tablicy
      // (na znanych zasadach inteligencji)
      status.quality=100;
      status.mode=STANDARDOWO;
      if (fident_obiekt_simple(mother,rozbior.obiekt,NULL,FULL_DEPTH,MODE_TOZSAMOSC)==FAKT_ZGODNY)
      {
         // nie obsîuguje sië wnioskowania przydawkowego
         if (status.mode==WNIOSKOWANIE_PRZYDAWKOWE) continue;

         quality=status.quality;

			// jeôli do tej pory max_quality byîo <intelligence, a teraz
			// jest quality>=intelligence, to zerujemy tablicë
			if (quality>=intelligence && quality_table<intelligence) ile_odp=0;

			// jeôli to pierwsza odpowiedú na liôcie to dopisujemy tak czy inaczej
			// a jeôli jest lista, to zaleûy, od wartoôci max_quality
			if (quality<intelligence && ile_odp>0)
			{
				// jeôli jakoôê odpowiedzi jest mniejsza od aktualnych na liôcie
				if (quality<quality_table) continue;
				// jeôli jest wiëksza, to kasujemy listë
				else if (quality>quality_table)
				{
					ile_odp=0;
				}
				// jeôli jest tej samej jakoôci, to dopisujemy dalej
			}

			if (ile_odp==0) quality_table=quality;

			// jeôli tablica jest peîna, to losowo nadpisujemy, lub nie
			if (ile_odp==MAX_INTELLIGENCE_TABLE)
			{
				if ((drand() % 2)==0) continue; // to nie dopisujemy
				// w przeciwnym razie dopisujemy pod jakimô losowym numerem
				odp_nr=(char) (drand() % MAX_INTELLIGENCE_TABLE);
			}
			else
			{
				ile_odp++;
				odp_nr=ile_odp-1;
			}

			fakty_table[odp_nr]=mother;
      }

      NEXT_MOTHER_FAKT: continue; // uchatek puchatek
   }

	if (view.odpowiedz==KOD_TRUE)
	{
		// rezultat sita inteligencji
		sprintf(txt,"sito inteligencji: (fakt) %d z %d (%d%%)\n",ile_odp,fakty_count(),quality_table);
		con_put(txt);
	}

   // jeôli nie ma odpowiedzi
   if (ile_odp==0)
   {
      con_put_komunikat(E_DENISE_PYTANIE_BRAK_DANYCH);
      return RESULT_OK;
   }

	// * * * INTUICJA * * *
	// losowanie odpowiedzi z listy
	odp_nr=(drand() % ile_odp); // odpowiedú od 0 do (ile_odp-1)

	if (view.odpowiedz==KOD_TRUE)
	{
		// rezultat sita intuicji
		sprintf(txt,"sito intuicji: nr %d z %d\n",odp_nr+1,ile_odp);
		con_put(txt);
	}

	ans_podmiotowe_show(fakty_table[odp_nr]);

   // zmiana tematu rozmowy
   temat.fakt=fakty_table[odp_nr];

   return RESULT_OK;
}

void FROM ans_podmiotowe_show(struct fakt_struct *fakt)
{
	char nr1;
	static struct odmiana_struct zdanie; // dlaczego do jasnej ma byê static!

   // dane o grupach (osobno podmiot z faktu)

	// grupa podstawowa
	if (fgrupa_get_body(fakt->obiekt_head->podstawowe,fakt->obiekt_head->funkc_head->opis[0],zdanie.podst[0])==RESULT_NO_OK)
      con_put("bîâd: kubuô 2 totalfatalista! (ans_podmiotowe_show)\n");

   // naturalizacja - raz na jakiô czas odpowiadamy jednym sîowem - podajâc sam podmiot!
   if ((drand() % 4)==0)
   {
      short_info.output=DENISE_OUTPUT;
      con_put_dialog(PODMIOT_DENISE,zdanie.podst[0],PRIORITY_ANS_ZG);
      return;
   }

	// funkcja, poziom, wyraz nadrzëdny
   zdanie.funkcja[0]=PODMIOT;
	zdanie.poziom[0]=0;
	zdanie.zwiazek[0]=-1;

	for (nr1=1;nr1<rozbior.obiekt->funkc_head->ile_grup;nr1++)
	{
		// grupa podstawowa
		if (fgrupa_get_body(rozbior.obiekt->podstawowe,rozbior.obiekt->funkc_head->opis[nr1],zdanie.podst[nr1])==RESULT_NO_OK)
         con_put("bîâd: kubuô 3 totalfatalista! (ans_podmiotowe_show)\n");

		// funkcja, poziom, wyraz nadrzëdny
      zdanie.funkcja[nr1]=rozbior.obiekt->funkcja[rozbior.obiekt->funkc_head->opis[nr1]];
		zdanie.poziom[nr1]=nr1;
		zdanie.zwiazek[nr1]=nr1-1;
	}
	zdanie.ile_grup=rozbior.obiekt->ile_grup;

   // wpisanie charakterystyki zdania
   zdanie.typ_podmiotu=PODMIOT_OKRESLONY;
	zdanie.podmiot_ident=PODMIOT_TEMAT;
	zdanie.podmiot=0;
	zdanie.orzeczenie=1;
   zdanie.twierdz_przecz=ZDANIE_TWIERDZACE;
   zdanie.oznajm_pyt=ZDANIE_OZNAJMUJACE;

	// wpisanie danych pomocniczych (skoro je posiadamy, to sië nimi dzielimy ;))
	zdanie.fakt=fakt;
	zdanie.obiekt=rozbior.obiekt;
	zdanie.simple=rozbior.obiekt->funkc_head;

	odmiana_main(&zdanie);

	// koniec odmiany
   short_info.output=DENISE_OUTPUT;
	con_put_dialog(PODMIOT_DENISE,zdanie.wynik,PRIORITY_ANS_ZG);
}

// * * * odpowiedú na pytanie szczegóîowe * * *

char FROM ans_szczegolowe(struct fakt_struct *fakt)
{
	// sprawdzenie FP - potwierdzenie, zaprzeczenie, lub brak danych

	status.quality=100;
	switch (fident_obiekt_simple(fakt,rozbior.obiekt,NULL,FULL_DEPTH,MODE_ZGODNOSC))
	{
		case FAKT_ZGODNY:
         if (status.quality==100) con_put_komunikat(E_DENISE_PYTANIE_ZGODNE);
         else con_put_komunikat(E_DENISE_PYTANIE_CHYBA_ZGODNE);
			break;
		case FAKT_SPRZECZNY:
         if (status.quality==100) con_put_komunikat(E_DENISE_PYTANIE_SPRZECZNE);
         else con_put_komunikat(E_DENISE_PYTANIE_CHYBA_SPRZECZNE);
			break;
		case FAKT_BRAK_DANYCH:
			con_put_komunikat(E_DENISE_PYTANIE_BRAK_DANYCH);
         break;
   }

   return RESULT_OK;
}

char FROM answer_main(struct fakt_struct *fakt)
{
   /*
   fakt - wskazuje na fakt, który zostaî wskazany przez pytanie (ident.)
   */

   if (view.odpowiedz==KOD_TRUE) con_put("\n* * * S Y N T E Z A  O D P O W I E D Z I * * *\n");

   // jeôli to tryb USER_MODE to bez przedstawienia sië nie ma rozmowy
   if (dtr_defined(PODMIOT_ROZMOWCA)==RESULT_NO_OK && mode==MODE_USER) return RESULT_OK;

   switch (rozbior.pytanie)
   {
		case PYTANIE_OGOLNE:
         if (view.odpowiedz==KOD_TRUE) con_put("odpowiedú na pytanie ogólne\n");
         return ans_ogolne(fakt);
		case PYTANIE_SZCZEGOLOWE:
         if (view.odpowiedz==KOD_TRUE) con_put("odpowiedú na pytanie szczegóîowe\n");
         return ans_szczegolowe(fakt);
		case PYTANIE_PODMIOTOWE:
         if (view.odpowiedz==KOD_TRUE) con_put("odpowiedú na pytanie podmiotowe\n");
         return ans_podmiotowe();

		// teoretycznie nigdy nie powinno wystâpiê, ale w koïcu lepiej zabezpieczyê
      default:
         return RESULT_NO_OK;
   }
}
