Nedala by se podmínka rošády nějak zredukovat? – .NET – Fórum – Programujte.com
 x   TIP: Přetáhni ikonu na hlavní panel pro připnutí webu
Reklama
Reklama

Nedala by se podmínka rošády nějak zredukovat? – .NET – Fórum – Programujte.comNedala by se podmínka rošády nějak zredukovat? – .NET – Fórum – Programujte.com

 

Hledá se programátor! Plat 1 800 € + bonusy (firma Boxmol.com)
Matěj Andrle+1
Grafoman
16. 8. 2015   #1
-
0
-

Dobrý den,
ve čtyř-směré šachové sestavě lze provést rošádu tahem z krále na věž, či z věže na krále. Dává to 16 možností.

if (selected.X == 0 && selected.Y == 0)
{
	if (target.Y == 0)
	{
		selected.X = 2;
		target.X = 1;
	}
	else
	{
		selected.Y = 2;
		target.Y = 1;
	}
}
if (target.X == 0 && target.Y == 0)
{
	if (selected.Y == 0)
	{
		selected.X = 2;
		target.X = 1;
	}
	else
	{
		selected.Y = 2;
		target.Y = 1;
	}
}

if (selected.X == 0 && selected.Y == 7)
{
	if (target.Y == 7)
	{
		selected.X = 2;
		target.X = 1;
	}
	else
	{
		selected.Y = 5;
		target.Y = 6;
	}
}
if (target.X == 0 && target.Y == 7)
{
	if (selected.Y == 7)
	{
		selected.X = 2;
		target.X = 1;
	}
	else
	{
		selected.Y = 5;
		target.Y = 6;
	}
}

if (selected.X == 7 && selected.Y == 7)
{
	if (target.Y == 7)
	{
		selected.X = 5;
		target.X = 6;
	}
	else
	{
		selected.Y = 5;
		target.Y = 6;
	}
}
if (target.X == 7 && target.Y == 7)
{
	if (selected.Y == 7)
	{
		selected.X = 5;
		target.X = 6;
	}
	else
	{
		selected.Y = 5;
		target.Y = 6;
	}
}

if (selected.X == 7 && selected.Y == 0)
{
	if (target.Y == 0)
	{
		selected.X = 5;
		target.X = 6;
	}
	else
	{
		selected.Y = 2;
		target.Y = 1;
	}
}
if (target.X == 7 && target.Y == 0)
{
	if (selected.Y == 0)
	{
		selected.X = 5;
		target.X = 6;
	}
	else
	{
		selected.Y = 2;
		target.Y = 1;
	}
}


Nemohu přijít na nic, čím bych podmínky sloučil - vždy pak něco nefunguje... selected i target mohou být králem i věží. (Právě ona obojakost rošády.) Z každého rohu to vede buď směrem nahoru, anebo dolů. Tak šustruji rohy a řídím se pozicí krále. Poněvadž nevím kdo je kdo, tak musím obě figurky otestovat na možnost kralování. Ano, nastavení oněch 2 proměnných by se dalo hodit do metody - já bych chtěl spojit podmínky...

Nahlásit jako SPAM
IP: 78.136.172.–
Reklama
Reklama
KIIV+42
God of flame
16. 8. 2015   #2
-
0
-

.net neznam, ale v C++ by se to dalo udelat nejak takto:

check_select(int cX, int cY) {
  if (selected.X==cX && selected.Y==cY) {
    if (target.Y==cY) {
      selected.X = (cX==7) ? 5 : 2;
      target.X   = (cX==7) ? 6 : 1;
    } else {
      selected.Y = (cY==7) ? 5 : 2;
      target.Y   = (cY==7) ? 6 : 1;
    }
  }
}
check_target(int cX, int cY) {
  if (target.X==cX && target.Y==cY) {
    if (select.Y==cY) {
      selected.X = (cX==7) ? 5 : 2;
      target.X   = (cX==7) ? 6 : 1;
    } else {
      selected.Y = (cY==7) ? 5 : 2;
      target.Y   = (cY==7) ? 6 : 1;
    }
  }
}
//...

check_select(0,0);
check_select(0,7);
check_select(7,0);
check_select(7,7);
check_target(0,0);
check_target(0,7);
check_target(7,0);
check_target(7,7);


pripadne predat i ty parametry select a target (a v prirazeni uz pouzivat ty tridni, aby se neprohazovaly taky)

check_universal(neco & a, neco & b, int cX, int cY) {
  if (a.X==cX && a.Y==cY) {
    if (b.Y==cY) {
      selected.X = (cX==7) ? 5 : 2;
      target.X   = (cX==7) ? 6 : 1;
    } else {
      selected.Y = (cY==7) ? 5 : 2;
      target.Y   = (cY==7) ? 6 : 1;
    }
  }
}


check_uni(select,target,0,0);
check_uni(select,target,0,7);check_uni(select,target,7,0);
check_uni(select,target,7,7);
check_uni(target,select,0,0);
check_uni(target,select,0,7);
check_uni(target,select,7,0);
check_uni(target,select,7,7);
// ci vetsi magie:
for (int i=0; i<8; ++i) {
  check_uni( ((i&4)?target:select), ((i&4)?select:target), ((i&2)?7:0), ((i&1)?7:0)); 
}
Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
Matěj Andrle+1
Grafoman
16. 8. 2015   #3
-
0
-

#2 KIIV
Nahradil jste větvení větvením - to už by bylo mnohem přehlednější nacpat nastavení dvojic "selected.X target.X" a "selected.Y ;target.Y" do metod. Jako s tím ternárním operátorem bych za měsíc ztratil pojem, jak to vlastně funguje... Takto vidím, že testuji rohy - ptám se v podstatě, zda je věží target anebo selected (zvolená a vyhazovaná figurka) -> ta druhá bude král. Jen si myslím, že by se daly alespoň 2 dvojice podmínek sloučit - neuvažuji nad ternárním operátorem - to jak píši, bych si pomohl z bláta do louže. Spíše bych chtěl odpočítávat od rohu - že bych proměnnou rohu nastavil na 0/7 a z toho nějak vycházel. Ovšem již se s tím peru moc dlouho - tak zkouším, zda někoho nenapadne svěží novinka.

Nahlásit jako SPAM
IP: 78.136.164.–
KIIV+42
God of flame
16. 8. 2015   #4
-
0
-

#3 Matěj Andrle
jo nahradil jsem 8vetveni jednim (nebo dvema). Kdyz zjistis chybu, tak to opravis jednou. A magie proto ze by to slo, i jednim cyklem, ne ze by to bylo zadouci.

Na malou ci velkou rosadu musis otestovat jestli je kral a vez na svoji startovni pozici a mista mezi nimi volne. Horsi je podminka, ze to jde jen v pripade, kdyz se s temi figurkami jeste vubec v cele partii netahlo!

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
Matěj Andrle+1
Grafoman
16. 8. 2015   #5
-
0
-

#4 KIIV
Obojí mám dávno pojištěno. Hra mi dokonale funguje. Nyní jsem ve zkrášlovací fázi - kdy už jen rejpu do svého kódu. Právě jak píši - spíše bych chtěl sloučit dvojice, kdy testuji na věž jak target, tak selected. (Což by zredukovalo 8 podmínek na 4 a to bych již byl spokojen.)

Nahlásit jako SPAM
IP: 78.136.164.–
Matěj Andrle+1
Grafoman
16. 8. 2015   #6
-
-1
-
Mimo téma

#4 KIIV
Těch větvení tam máte skoro stejně. Co si myslíte, že je else + ternární operátor + ...? A o názvech proměnných mlčím dočista. V přehlednosti vede můj kód.

Nahlásit jako SPAM
IP: 78.136.164.–
KIIV+42
God of flame
16. 8. 2015   #7
-
0
-

Jenze ty sem davas realny kod, ja jen priklad, ktery jsem dal dohromady za par minut.

Chtel jsi to zjednodusit - to jde, ale spis na vyssi urovni - napriklad predas do source vzdy krale, do target vzdy vez. Zaroven vis, jestli je to cernej nebo bilej tah, takze podle toho muzes testovat uz jen spravnej radek.

A resis velkou rosadu? tam se presouvaji blize ke krali, ne k vezi (jelikoz jsou tam 3 mista).

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
Matěj Andrle+1
Grafoman
16. 8. 2015   #8
-
0
-

#7 KIIV
Myslel jsem, že u velké je to také blíže k věži. Tak na to se juknu - to už není žádný problém... Sloučení se mi zdařilo takto:

bool selectedIsRook, targetIsRook = false;

if
(
	(selectedIsRook = (selected.X == 0 && selected.Y == 0)) ||
	(targetIsRook = (target.X == 0 && target.Y == 0))
)
{
	if
	(
		(selectedIsRook && target.Y == 0) ||
		(targetIsRook && selected.Y == 0)
	)
	{
		selected.X = 2;
		target.X = 1;
	}
	else
	{
		selected.Y = 2;
		target.Y = 1;
	}
}
Nahlásit jako SPAM
IP: 78.136.165.–
KIIV+42
God of flame
16. 8. 2015   #9
-
0
-

Kazdopadne vubec nechapu, co vlastne tedy znamena  X a Y, kdyz tedy ocividne ne sloupec/radek...  jedinej test na radek bych videl jestli je Y 0 nebo 7 (na sachovnici  1 nebo 8) a pak uz jen prohazovat pozice figurek na tom samem radku.

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
Matěj Andrle+1
Grafoman
16. 8. 2015   #10
-
0
-

#9 KIIV
S velkou rošádou (otestováno - ve všech 4 směrech funguje):

if (selected.X == 0 && selected.Y == 0)
{
	if (target.Y == 0)
	{
		selected.X = 3;
		target.X = 2;
	}
	else
	{
		selected.Y = 2;
		target.Y = 1;
	}
}
if (target.X == 0 && target.Y == 0)
{
	if (selected.Y == 0)
	{
		selected.X = 3;
		target.X = 2;
	}
	else
	{
		selected.Y = 2;
		target.Y = 1;
	}
}

if (selected.X == 0 && selected.Y == 7)
{
	if (target.Y == 7)
	{
		selected.X = 3;
		target.X = 2;
	}
	else
	{
		selected.Y = 4;
		target.Y = 5;
	}
}
if (target.X == 0 && target.Y == 7)
{
	if (selected.Y == 7)
	{
		selected.X = 3;
		target.X = 2;
	}
	else
	{
		selected.Y = 4;
		target.Y = 5;
	}
}

if (selected.X == 7 && selected.Y == 7)
{
	if (target.Y == 7)
	{
		selected.X = 5;
		target.X = 6;
	}
	else
	{
		selected.Y = 4;
		target.Y = 5;
	}
}
if (target.X == 7 && target.Y == 7)
{
	if (selected.Y == 7)
	{
		selected.X = 5;
		target.X = 6;
	}
	else
	{
		selected.Y = 4;
		target.Y = 5;
	}
}

if (selected.X == 7 && selected.Y == 0)
{
	if (target.Y == 0)
	{
		selected.X = 6;
		target.X = 5;
	}
	else
	{
		selected.Y = 2;
		target.Y = 1;
	}
}
if (target.X == 7 && target.Y == 0)
{
	if (selected.Y == 0)
	{
		selected.X = 6;
		target.X = 5;
	}
	else
	{
		selected.Y = 2;
		target.Y = 1;
	}
}


Jedná se mi o naprosto objektivní návrh - vše je zkrátka natolik obecné, že je možné aplikovat do stejného mechanismu dalších X her. Pročež nepočítám se 2 hráči, ani se 2 jednoduchými směry atp. Počítám s XY možnostmi. Nechápu, že nechápete, že přesně co píšete testuji. Testuji právě, zda jsme v rohu X a zda v tomto rohu jsme ve směru horizontálním, anebo vertikálním. Na základě toho pak provedu velkou, či malou rošádu. (Otáčení po směru ručiček.)

Nahlásit jako SPAM
IP: 78.136.165.–
KIIV+42
God of flame
16. 8. 2015   #11
-
0
-

#10 Matěj Andrle
Budu hadat, to znamena to 4-smere  -  jsem si rikal, co je to za blbost. Budiz, pak to prohazovani na Y dava smysl.

Takova mira abstrakce a stejne pouzivas magicky konstanty - co kdyz bude nekdo chtit zvetsit pole? Najednou tu mas 54 potencialnich mist, kde to musis zmenit (samo ne vsude, jelikoz nektere konstanty se vazou na 0). A to jen v tom kodu z predchoziho prispevku.

#8 Matěj Andrle
jeste k tomuhle kodu:
(selectedIsRook = (selected.X == 0 && selected.Y == 0)) || (targetIsRook = (target.X == 0 && target.Y == 0))
To muzes mit vez jen na pozici [0,0] ? Nebo aspon popis o co jde. Nemas tam zadne komentare a kod neni ani zdaleka "selfcommenting".

Proc nepouzivas objekty, kde budes mit i co je to za figurku?

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
Matěj Andrle+1
Grafoman
16. 8. 2015   #12
-
0
-

#11 KIIV
Toto je dynamické pole! Vůbec jste můj návrh neviděl a kritizujete jej... :S Mám spoustu proměnných k identifikaci, validaci a dalšímu nakládání s figurkami. Kupříkladu herní mapu abstraktní třídy Piece (šablona figurky) - null/Piece. Mapu možností pohybu - na abstraktní třídě Piece FillWithMovements naplní možnostmi každé figurky. Atd.

Nahlásit jako SPAM
IP: 78.136.165.–
Matěj Andrle+1
Grafoman
16. 8. 2015   #13
-
0
-

#11 KIIV
http://leteckaposta.cz/783378548

Nyní můžete kritizovat. Oč jsem však vůbec nežádal - viz úvodní příspěvek. (Obsahuje jasnou zmínku o možnostech změny směru atp.)

Nahlásit jako SPAM
IP: 78.136.165.–
KIIV+42
God of flame
16. 8. 2015   #14
-
0
-

to je super, dynamicke pole, ale vez muze stat jen na pozici [0,0] [0,7] [7,0] a [7,7]

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
Matěj Andrle+1
Grafoman
16. 8. 2015   #15
-
0
-

#14 KIIV
Jak, když jsem otestoval, že se nehnula? Kód jste neviděl, avšak moudrosti chrlíte... :S

Nahlásit jako SPAM
IP: 78.136.165.–
KIIV+42
God of flame
16. 8. 2015   #16
-
0
-

#15 Matěj Andrle
co je potom napriklad toto:
if (selected.X == 7 && selected.Y == 7)

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
Matěj Andrle+1
Grafoman
16. 8. 2015   #17
-
0
-

#16 KIIV
Vím, že se nehnula - kde jinde by měla být?

Nahlásit jako SPAM
IP: 78.136.188.–
KIIV+42
God of flame
16. 8. 2015   #18
-
0
-

Z kodu Bishop.cs:

Nepouzivani { } pro jeden prikaz je potencialni zdroj chyb. Jednou zapomenes a dela to neco uplne jinyho.

MAGICKE KONSTANTY:  x < 8 && y < 8;    chci videt, jak zvetsis to tvoje DYNAMICKE POLE na 10x12

Zbytecne promenne jako x, y, kdyz se to da vypocitat pouzitim jedine promenne treba i jako posun. 

Zbytecne moc cyklu, kdyz se to da dat do jednoho (za predpokladu, ze budes pouzivat  this.X +- i / this.Y +- i) s pripadnym omezenim pomoci nejakeho bool ze uz si dosahl konce pro danny smer

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
Matěj Andrle+1
Grafoman
16. 8. 2015   #19
-
0
-

#18 KIIV
Tyto figurky se vážou překvapivě na hru šachy. Ano - u této hry se jedná o konstantu. Ovšem u mého dynamického pole se velikost odvíjí od typu hry! Viz PieceSet atd.

Nahlásit jako SPAM
IP: 78.136.188.–
Evzen+2
Návštěvník
2. 9. 2015   #20
-
0
-

#18 KIIV
Nemá to smysl se s ním hádat, Matěj nechce poradit, jen se chtěl pochlubit :)

Nahlásit jako SPAM
IP: 88.101.0.–
Matěj Andrle+1
Grafoman
2. 9. 2015   #21
-
0
-

#20 Evzen
Pochlubit čím asi? Copak se z té podmínky dá cokoliv vyčíst? Šlo mi o její redukci, či ještě lépe eradikaci. Předložil jsem vzorec a chtěl jsem z něj vyvodit jiný - k tomu není třeba čehokoliv jiného. Že mi poradí nahradit větvení větvením, kteréžto navíc kód ještě znepřehlední - to mám přijmout? Já spíš očekával nějaký výpočet/přepočet/... a třeba kombinovaný mapou (slovník, pole, ...). Mne nenapadá doposud, jak se zde vyhnout větvení. Ovšem rád bych se poučil.

Nahlásit jako SPAM
IP: 78.136.190.–
Ovrscout
~ Anonymní uživatel
72 příspěvků
2. 9. 2015   #22
-
0
-

#21 Matěj Andrle
hmpf, podle prvního příspěvku mi to nepřijde nějak moc vhodné k zjednodušení na úrovni podmínek. Možná by šlo sloučit některé části podmínek(např selected.X == 0 atp.) a vytvořit tak hlubší vnoření podmínek to by ale na přehlednosti moc nepřidalo a if-ů  by také nebylo méně, ale mohlo by to pomoct rychlostně.
Ale když už jste/jsi nakousl mapu,pole,slovník, Co tak zkusit z toho udělat něco jako seznam tahů

tj. pole ve smyslu: (Omluvte mou klačtinu můj prasozápis v C jakožto názvy,typedef a podobné)

typedef struct {
       //pozadovana vstupni konfigurace
       Point target_in;
       Point select_in;

       //vystup - pokud plati vstupni konfigurace
       Point target_Out;
       Point select_Out;
}TZnamyTah;

TZnamyTah ZnameTahy[]={...ze doplnit...}

Toto pole by se pak jednoduše prošlo a při souhlasících pozicích target a select by se výstup přepsal tím co je v poli uloženo jako out a ukončilo by se procházení, (nebo ne pokud i další položka má stejné vstupní hodnoty).
Jisté optimalizace by se možná dalo dosáhnout pokud by pole bylo setříděno v
pořadí:target_in.x, target_in.y,select_in.x,select_in.y . Potom by se dalo procházení pole "optimalizovat" tak že by se nejdříve našla řádka která má správnou první souřadnici, pak by se pokračovalo kontrolou druhé, třetí, čtvrté.
Nabo případně když už to bude tabulka, tak záznamy vložit do hashtabulky (Hash ze všech vstupních souřadnic),ale zas záleží jak rychlá bude hash funkce a hledání v hashtabulce.
A samozřejmně záleží na počtu podmínek, zda by se to vyplatilo a je nutno to změřit.

Dálší vylepšení mohou být např generování tabulky dle rozměrů a počtu stran místo statické tabulky. A pokud už budete tabulku generovat tak třeba bude možné místo tabulky použít iterátor/generátor ke generování položek za běhu(asi yield nebo tak něco se na to používá) - to ale zas nepoužije hash tabulku.

A kdo ví, možná že z té tabulky bude vidět něco co z toho zápisu s podmínkami není vidět a napadne vás nějaký lepší způsob.

P.S. Teď koukám že v podmínkách je i !=0 (respektive else k ==0). Pro klasickou rošádu (já šachy moc neznám takže dle wiki)musí být obě figurky na výchozích pozicích, čili místo !=0 lze testovat konkrétní pozici.
Pokud by to však bylo nutné pro vaše vícerozměrné šachy tak by mohlo situaci zkomplikovat, nejspíše přidáním příznaku pro "žolíkování" danné souřadnice pro dannou položku pole.

Nahlásit jako SPAM
IP: 193.165.79.–
Zjistit počet nových příspěvků

Přidej příspěvek

Toto téma je starší jak čtvrt roku – přidej svůj příspěvek jen tehdy, máš-li k tématu opravdu co říct!

Ano, opravdu chci reagovat → zobrazí formulář pro přidání příspěvku

×Vložení zdrojáku

×Vložení obrázku

Vložit URL obrázku Vybrat obrázek na disku
Vlož URL adresu obrázku:
Klikni a vyber obrázek z počítače:

×Vložení videa

Aktuálně jsou podporována videa ze serverů YouTube, Vimeo a Dailymotion.
×
 
Podporujeme Gravatara.
Zadej URL adresu Avatara (40 x 40 px) nebo emailovou adresu pro použití Gravatara.
Email nikam neukládáme, po získání Gravatara je zahozen.
-
Pravidla pro psaní příspěvků, používej diakritiku. ENTER pro nový odstavec, SHIFT + ENTER pro nový řádek.
Sledovat nové příspěvky (pouze pro přihlášené)
Sleduj vlákno a v případě přidání nového příspěvku o tom budeš vědět mezi prvními.
Reaguješ na příspěvek:

Uživatelé prohlížející si toto vlákno

Uživatelé on-line: 0 registrovaných, 58 hostů

 

Hostujeme u Českého hostingu       ISSN 1801-1586       ⇡ Nahoru Webtea.cz logo © 20032016 Programujte.com
Zasadilo a pěstuje Webtea.cz, šéfredaktor Lukáš Churý