Jump to content
BulForum.com

"Бикове и крави" на PHP


Recommended Posts

Значи, правих Бикове и крави на PHP и този, на който трябваше да го предавам е далеч от мен, затова пишем по ел.поща. След като го предадох получих съобщение с коментари, което не мога да разбера. Искам, ако може, някой по-опитен уеб дизайнер да ми разкодира следните думи:

Здравей след преглед на кода ето какви са забележките на IT Мениджъра който иска да оправиш след което да изпратиш наново:

 

Цитат:

 

iskame tekstovete i opciite da sa v otdelen file.

 

da ne zamqrsyavame tolkova namespace s imena na funkcii - da pomislim kak moje da stane.

 

i funkcionalnostta da e otdelena ot web prilojenieto - nay-veche po-razumen error handling ot gruboto die()

 

Ето и сорса, ако ще помогне да разберете, какво не им харесва:

iface.php

<!-- INTERFACE -->

<?php include "engine.php"; ?>

<html>
<head>
<title>Bulls & Cows - The popular game for timewasting!</title>
<style type="text/css">
	TD{background-color:white;font-family:verdana}
</style>
</head>
<body>
<form name="form1" action="iface.php" method="post">
	<table border="0" cellspacing="1" cellpadding="3" bgcolor="#353535" align="center">
		<tr>
			<td width="50%" align="center">Your suggestion:</td>
			<td bgcolor="#FFFFFF" colspan=2>
				<input type="text" name="Number" maxlength=4>
			</td>
		</tr>
		<tr>
			<td bgcolor="#FFFFFF" colspan=3 align="center">
				<input type="submit" name="Submit" value="New Game">
				<input type="submit" name="Submit" value="Check">
				<input type="submit" name="Submit" value="Hint">
				<input type="submit" name="Submit" value="Records">
				<input type="submit" name="Timeout" value="Timeout" style="display: none;">
				<?
					if (empty($my_array) == FALSE) {
						foreach ($my_array as $key => $value) {
							echo '<input type=hidden name="my_array[]" value="'.htmlspecialchars($value).'">';
						}
					}
				?>
				<input type="hidden" name="realval" value="<? echo $realval ?>">
				<input type="hidden" name="tmstmp" value="<? echo $tmstmp ?>">
				<input type="hidden" name="hops" value="<? echo $hops ?>">
				<input type="hidden" name="rec" value="<? echo $rec ?>">
			</td>
		</tr>
		<?
			if (empty($my_array) == FALSE) {
				foreach ($my_array as $rowstr) {
					echo "<tr><td bgcolor=\"#FFFFFF\" colspan=3 align=\"center\">".$rowstr."</td></tr>";
				}
				if (substr(end($my_array), 0, strlen("You win!")) == "You win!") {
					echo "
							<tr>
								<td><input type=\"hidden\" name=\"time\" value=\"".$time."></td>
								<td width=\"33%\" align=\"center\"><center>Your name:</center></td>
								<td bgcolor=\"#FFFFFF\" width=\"33%\">
									<input type=\"text\" name=\"Winner\" maxlength=10>
								</td>
								<td bgcolor=\"#FFFFFF\" width=\"33%\">
									<center><input type=\"submit\" name=\"Submit\" value=\"Record\"></center>
								</td>
							</tr>";
				}
			}
		?>
	</table>
</form>

<?php
if ($_POST['Timeout'] != "Timeout" && ($_POST['Submit'] == "New Game" || $_POST['Submit'] == "Check" || $_POST['Submit'] == "Hint"))
echo "
<!-- Timeout implementation -->
<script language=\"Javascript\">
function submit() {
	document.form1.Timeout.click();
}
setTimeout(\"submit()\", 5*60*1000);
</script>

<!-- The visible timer countdown -->
<center>Time remaining: <span id=\"seconds\">300</span>s.</center>
<script>
	var seconds = 300;
		setInterval(
			function () {
				document.getElementById('seconds').innerHTML = --seconds;
			}, 1000
		);
</script>
";
?>
</body>
</html>

engine.php

<!-- ENGINE -->

<?php include "func.php"; ?>
<?php
/* CHECKING IF TIMEOUT OCCURED */
if ($_POST['Timeout'] == "Timeout"){
	$my_array = array();
	$my_array[] = "Timeout! You lose.";
}

switch ($_POST['Submit']) {
	/* FORM HAS BEEN SUBMITTED WITH NEW GAME */
	case "New Game":
		$realval = ngen();
		$tmstmp = time();
		$hops = 0;
		$my_array = array();
		break;

	/* FORM HAS BEEN SUBMITTED WITH CHECK */
	case "Check":
		$val = $_POST['Number'];
		$realval = $_POST['realval'];
		$tmstmp = $_POST['tmstmp'];
		$hops = $_POST['hops'] + 1;
		$my_array = $_POST['my_array'];
		if ($_POST['rec'] == 1)
			unset($my_array);
		$result = cmpr($val, $realval);
		if ($result == "You win!") {
			$time = time() - $tmstmp;
			unset($realval, $tmstmp, $my_array);
			$result = $result." Your time: ".$time." sec. You tried it ".$hops." times.";
		}
		$my_array[] = $result;
		break;

	/* FORM HAS BEEN SUBMITTED WITH HINT */
	case "Hint":
		$my_array = array();
		$val = $_POST['Number'];
		$realval = $_POST['realval'];
		$tmstmp = $_POST['tmstmp'];
		$hops = $_POST['hops'] + 1;
		$my_array = $_POST['my_array'];
		$hintfound = 0;
			if (empty($my_array) == FALSE) {
				if (strlen(end($my_array)) == 4) {
					$hintfound = 1;
					$str = end($my_array);
					for ($i=0,$stars=0; $i<4; $i++) {
						if ($str[$i] == '*')
							$stars++;
					}
				}
			}
		if ($hintfound == 0) {
			$my_array[] = givehint($realval, 3);
		}
		else {
			$my_array[] = givehint($realval, $stars-1);
		}
		break;

	/* FORM HAS BEEN SUBMITTED WITH RECORDS */
	case "Records":
		$my_array = array();	
		$rec = 1;
		$connect = mysql_connect("x.x.x.x", "usrx", "pssx") or die("Sorry, unable to connect to DB...");
		mysql_select_db("bullscows", $connect) or die("DB selection failed: ".mysql_error());
		$query = "SELECT name, time, hops FROM records
					ORDER BY time, hops
					LIMIT 10;
					";
		$results = mysql_query($query) or die('Query failed: ' . mysql_error());
		while ($line = mysql_fetch_array($results)) {
			foreach ($line as $row) {
				$my_array[] = $row;
			}
		}
		break;

	case "Record":
		$name = $_POST['Winner'];
		$time = $_POST['time'];
		$hops = $_POST['hops'];
		rectodb($name, $time, $hops);
		break;
	default:
		break;
}
?>

func.php

<!-- FUNCTION DEFINITIONS -->

<?php
// compare user's number and the real one
function cmpr ($usrn, $realn) {
$bulls = 0;
$cows = 0;
for ($i=0; $i<4; $i++) {
	for ($j=0; $j<4; $j++) {
		if ($usrn[$i] == $realn[$j] && $i == $j) {
			$bulls++;
			break;
		}
		else {
			if ($usrn[$i] == $realn[$j] && $i != $j) {
				$cows++;
				break;
			}
		}
	}
}
if ($bulls == 4)
	return "You win!";
return $usrn.": ".$bulls." bull(s), ".$cows." cow(s)";
}

// check a generated number for reoccurences
function chck_n ($n) {
for ($i=0; $i<3; $i++) {
	for ($j=$i+1; $j<4; $j++) {
		if ($n[$i] == $n[$j])
			return 1;
	}
}
return 0;
}

// generate a random number
function ngen () {
do {
	$rval = rand(1023, 9876);
}
while (chck_n(strval($rval)) == 1);
return $rval;
}

// return a string in the form of a hint
function givehint ($num, $st) {
$hint = strval($num);
for ($i=0; $i<$st; $i++) {
	$hint[3-$i] = '*';
}
return $hint;
}

// record to DB
function rectodb ($name, $time, $hops) {
$connect = mysql_connect("x.x.x.x", "usrx", "pssx") or die("Sorry, unable to connect to DB...");
mysql_select_db("bullscows", $connect) or die("DB selection failed: ".mysql_error());
$query = "INSERT INTO `bullscows`.`records` (`name`, `time`, `hops`)
			VALUES ('$name', '$time', '$hops');
			";
$res = mysql_query($query) or die('Query failed: ' . mysql_error());
mysql_close($connect);
}
?>

 

Ето линк: http://87.246.61.61/iface.php, да видите как работи... Моля, помогнете ми, че е важно. :( Мерси предварително!

Link to comment
Share on other sites

:)

Тоя ИТ мениджър му кажи да си гледа работата :) .

Не знам дали това е вид тест за твоите умения, но той трябва да е наясно, че всичко според обема и изискванията на задачата.

Тук само за error-handling-a съм по-съгласен.

die() е най-често ползвания начин по разните примери и по-прости туториали. Но на тях не им е и целта да правят error handling в примерите, те примерите затова са примери.

 

В PHP можеш да ползваш ексепшъни, но това в случаите, когато даден код генерира такъв.

Примерно свързването с базата връща false при неуспех.

Най-просто, поне е добре да хващаш тези случаи и културно да завършиш хтмл кода, примерно с някое добре оформено съобщение, вкл. съобщението, върнато от mysql_error().

 

За текстовете и опциите - не прегледах обстойно файловете, но кои текстове и кои опции?

Да нямат предвид разделянето на отделните логически елементи от страницата в отделни инклудета? Аз примерно така правя с главни менюта, леви/десни рекламни колони, хедъри, футъри..

 

Да не замърсяваме "namespace" s имена на ф-ии?!

Тези хора наясно ли са, че namespace-и има едва от PHP 5.3, при това 5.3 да намериш инсталиран някъде, е все още рядкост? Ако са употребили термина, повлияни от познанията си от други езици, тогава моля, да не объркват читателя (теб), понеже ти може да не знаеш какво е клас, те за намеспацес ще говорят.

Имаш 3 функции на кръст, не виждам какъв намеспаце замърсяваш. Или искат тази проста задача да я напишеш с обекти? Тогава сигурно ще замърсим неймспейса с имена на класове :) .

 

Функционалността да е отделена от приложението.

Това да. Принципно. Ако стигнеш по-далече, ползваш темплейти (Smarty или нещо такова, макар че смарти е тъпо в този малък случай).

" nay-veche po-razumen error handling ot gruboto die()" - каква точно връзка има това с разделението на функционалността в случая?!

Ти тоя error handling, e ясно че няма и не го правиш там, където вече започваш да извеждаш хтмл-а.

 

Според мен и те не знаят какво искат. Или ти не си казал с каква цел е занятието.

Link to comment
Share on other sites

За текстовете и опциите - не прегледах обстойно файловете, но кои текстове и кои опции?

Ами текстовете мисля, че разбрах кои са - тия стрингове в engine.php, от вида "Timeout! You lose" да не са пльоснати ей така, а да са констатни низове, дефинирани в отделен файл. Май е това.

Функционалността да е отделена от приложението.

Това да. Принципно. Ако стигнеш по-далече, ползваш темплейти (Smarty или нещо такова, макар че смарти е тъпо в този малък случай).

Тук имаха предвид да са разделени интерфейса и смятащата "машина", за да може тя да се ползва за игра и през други интерфейси, например WAP форми, SMS-и и т.н. Но аз си мислех, че това съм го постигнал, като съм сложил html формата в iface.php, а решаващата логика в engine.php и съм ги plug-нал с един include. Не знам, явно се иска нещо друго.

Link to comment
Share on other sites

Ми вместо да хвърлят някакви мъгляви изисквания за разделение, да кажат за какво ще е нужно, за да се направи съответната корекция.

Ако ще се ползва като съвсем отделен модул, то винаги има какво да се направи по интерфейса (нямам предвид хтмл-то което се извежда) и модулирането на нещата, и да се разграничи още изчисленията от изхода.

Абе изобщо от подхвърлените 1-2 изречения в отговора им, не става ясно какво точно искат :) .

Може би искат фунцкионалността да е така изградена, че да не зависи от конкретния интерфейс (хтмл, аутпут, както искаш го наречи). В този случай с класове нещата може да станат по-добре.

Не съм разгледал обстойно дългите файлове.

 

За текстовете ясно. Така или иначе винаги е добре да се отделят лейбълите в отделен language файл (примерно). Аз така ги отделям. Отделно че позволява мултиезични приложения.

Link to comment
Share on other sites

Добре, почнах да го правя с класове. Цялата информация, която трябва да бъде показана във формата ще е обект. Ще го сериализирам и след това ще го предавам с масива $_SESSION между отделните изпълнения на скрипта. Как ти се струва?

А "текстовете" и лейбълите ще ги направя константни низове в отделен файл, и ще го включвам. Дори в html формата ще се виждат само променливи и никакъв текст, напр:

<input type="submit" name="Submit" value=<? echo $someshit ?>>

и

<td width="50%" align="center"><? echo $somemoreshit?></td>

Надявам се това вече да е достатъчната "отделеност" на функционалност от интерфейс...

Link to comment
Share on other sites

Ми зависи какво ще им щукне на тях :)

Обект да ползваш, ако ще се плъгва скрипта ти в нещо по-голямо примерно.

С функции си беше добре принципно.

 

Ми да, то няма как иначе, отделяйки лейбълите, и ги ръгаш така където трябва.

Само на твое място бих избягвал <? таговете. Т.е. asp стил. те са опция и не са универсални, зависи дали са пуснати в конфа. Повечето не са и няма да работят.

 

Каква е идеята да го сериализираш обекта и да го предаваш през session? Нужен ли ще е да се пази между отделните изпълнения?

Вместо това можеш да си пазиш в сесията някакви други прости данни. Така или иначе ако ползваш сесия, ще се предава сесиен ключ по куки.

Това ти ще си решиш, на мен лично досега не ми се е налагало и не съм намирал причина да пазя в сесията цели обекти.

Link to comment
Share on other sites

Warning: Unknown: write failed: No space left on device (28) in Unknown on line 0

Warning: Unknown: Failed to write session data (files). Please verify that the current setting of session.save_path is correct (/var/lib/php5) in Unknown on line 0

Това се получава при нова игра. Ако опитам да въвеждам директно и да чеквам нищо не става също.

Link to comment
Share on other sites

Warning: Unknown: write failed: No space left on device (28) in Unknown on line 0

Warning: Unknown: Failed to write session data (files). Please verify that the current setting of session.save_path is correct (/var/lib/php5) in Unknown on line 0

Това се получава при нова игра. Ако опитам да въвеждам директно и да чеквам нищо не става също.

Очевидно човека го е направил със сесия, и не е доконфигурирал опциите в php.ini за сесии. Ако иска сесии, трябва да се подготви за тях, а явно не е. Пътища, пермисии, най-добре да си създаде отделна директория за тях.

Само нямам спомен дали преди ползваше сесии.

Link to comment
Share on other sites

No space left on device (28)

Тия дни наистина ми се препълни дяла, понеже се опитвах да си компилирам gcc-3.3, а той се оказа една голяааама колекция... Сигурно от това е било.

Link to comment
Share on other sites

Archived

This topic is now archived and is closed to further replies.

×
×
  • Create New...