1. Trang chủ
  2. » Công Nghệ Thông Tin

PHP 5/MySQL Programming- P38 doc

5 266 0
Tài liệu đã được kiểm tra trùng lặp

Đang tải... (xem toàn văn)

THÔNG TIN TÀI LIỆU

Thông tin cơ bản

Định dạng
Số trang 5
Dung lượng 115,87 KB

Các công cụ chuyển đổi và chỉnh sửa cho tài liệu này

Nội dung

Building the Program’s Main Logic The main logic for the program begins by retrieving the word list and puzzle parameters from the user’s form.. Then it tries to convert the list into an

Trang 1

Building the Program’s Main Logic

The main logic for the program begins by retrieving the word list and puzzle

parameters from the user’s form Then it tries to convert the list into an array

This type of text analysis is sometimes called parsing

The program then repeatedly tries to build the board until it succeeds Once the

program has successfully created the board, it creates an answer key and adds

the random letters with the addFoils()function Finally, the program prints the

completed puzzle

} else {

//get puzzle data from HTML form

$boardData = array(

width => $width,

height => $height,

name => $name

);

//try to get a word list from user input

if (parseList() = = TRUE){

$legalBoard = FALSE;

//keep trying to build a board until you get a legal result

while ($legalBoard = = FALSE){

clearBoard();

$legalBoard = fillBoard();

} // end while

//make the answer key

$key = $board;

$keyPuzzle = makeBoard($key);

//make the final puzzle

addFoils();

$puzzle = makeBoard($board);

//print out the result page

printPuzzle();

} // end parsed list if

} // end word list exists if

163

l i

Trang 2

You should be able to tell the general program flow even if you don’t understand exactly how things happen The main section of a well-defined program should give you a bird’s eye view of the action Most of the details are delegated to functions Most of the remaining chapter is devoted to explaining how these functions work Try to make sure you’ve got the basic gist of the program’s flow; then you see how all of it is done

Parsing the Word List

One important early task involves analyzing the word list that comes from the user The word list comes as one long string separated by newline (\n) characters

other important functions too, including converting each word to uppercase, checking for words that do not fit in the designated puzzle size, and removing unneeded carriage returns

function parseList(){

//gets word list, creates array of words from it

//or return false if impossible

global $word, $wordList, $boardData;

$itWorked = TRUE;

//convert word list entirely to upper case

$wordList = strtoupper($wordList);

//split word list into array

$word = split(“\n”, $wordList);

foreach ($word as $currentWord){

//take out trailing newline characters

$currentWord = rtrim($currentWord);

//stop if any words are too long to fit in puzzle

if ((strLen($currentWord) > $boardData[“width”]) &&

(strLen($currentWord) > $boardData[“height”])){

print “$currentWord is too long for puzzle”;

$itWorked = FALSE;

} // end if } // end foreach

return $itWorked;

} // end parseList

164

g r

s o

l u

g in

e r

Trang 3

l i

The first thing I did was use the strtoupper()function to convert the entire word

list into uppercase letters Word search puzzles always seem to use capital letters,

so I decided to convert everything to that format

The long string of characters with newlines is not a useful format here, so I

con-verted the long string into an array called $word The split()function works

per-fectly for this task I split on the string “\n” This is the newline character, so it

should convert each line of the text area into an element of the new $wordarray

The next task was to analyze each word in the array with a foreachloop When I

tested this part of the program, it became clear that sometimes the trailing

new-line character was still there, so I used the rtrim() function to trim off any

unnecessary trailing whitespace

It is impossible to create the puzzle if the user enters a word larger than the

height or width of the puzzle board, so I check for this situation by comparing

the length of each word to the board’s height and width Note that if the word is

too long, I simply set the value of the $itWorkedvariable to FALSE

Earlier in this function, I initialized the value of $itWorkedto TRUE By the time

the function is finished, $itWorked still contains the value TRUEif all the words

were small enough to fit in the puzzle If any of the words were too large, the

value of $itWorkedis FALSEand the program stops

Clearing the Board

(boards which contain all the words in the list) It creates random boards

repeat-edly until it finds one that is legal While this may seem like a wasteful approach,

it is much easier to program than many more sophisticated methods and

pro-duces remarkably good results for simple problems

I N THE R EAL W ORLD Although this program does use a brute force approach to find a good solution,

you see a number of ways the code is optimized to make a good solution more

likely One example of this is the way the program stops if one of the words is

too long to fit in the puzzle This prevents a long processing time while the

pro-gram tries to fit a word in the puzzle when it cannot be done A number of other

places in the code do some work to steer the algorithm toward good solutions

and away from pitfalls Because of these efforts, you find that the program is

actually pretty good at finding word search puzzles unless there are too many

words or the game board is too small.

Trang 4

The game board is often re-created several times during one program execution.

I needed a function that could initialize the game board or reset it easily The game board is stored in a two-dimensional array called $board When the board

is “empty,” each cell contains the period (.) character I chose this convention because it gives me something visible in each cell and provides a character that represents an empty cell The clearBoard() function sets or resets the $board array so that every cell contains a period

function clearBoard(){

//initialize board with a in each cell

global $board, $boardData;

for ($row = 0; $row < $boardData[“height”]; $row++){

for ($col = 0; $col < $boardData[“width”]; $col++){

$board[$row][$col] = “.”;

} // end col for loop } // end row for loop

} // end clearBoard

This code is the classic nested forloop so common to two-dimensional arrays Note that I used forloops rather than foreachloops because I was interested in the loop indices The outer forloop steps through the rows Inside each row loop, another loop steps through each column I assigned the value “.”to the $boardarray at the current $rowand $collocations Eventually, “.”is in every cell in the array

I determined the size of the for loops by referring to the $boardData associative array Although I could have done this a number of ways, I chose the associative array for several reasons The most important is clarity It’s easy for me to see by this structure that I’m working with the height and width related to board data Another advantage in this context is convenience Since the height, width, and board name are stored in the $boardData array, I could make a global reference

to the $boardData variable and all its values would come along It’s like having three variables for the price of one.

Filling the Board

Of course, the purpose of clearing the board is to fill it in with the words from the word list This happens in two stages: filling the board, and adding the words

board, but the details of adding each word to the board are relegated to the

T R I C K

166

g r

s o

l u

g in

e r

Trang 5

The board is only complete if each word is added correctly Each word is added only

if each of its letters is added without problems The program calls fillBoard()as

often as necessary to get a correct solution Each time fillBoard()runs, it may

call addWord()as many times as necessary until each word is added The addWord()

function in turn keeps track of whether it is able to successfully add each

char-acter to the board

The general fillBoard()function plan is to generate a random direction for each

word and then tell the addWord()function to place the specified word in the

spec-ified direction on the board

The looping structure for the fillBoard()function is a little unique, because the

loop could exit two ways If any of the words cannot be placed in the requested

manner, the puzzle generation stops immediately and the function returns the

value FALSE However, if the entire word list is successfully placed on the game

board, the function should stop looping, but report the value TRUE

You can achieve this effect a number of ways, but I prefer often to use a special

Boolean variable for this purpose Boolean variables are variables meant to contain

only the values TRUEand FALSE Of course, PHP is pretty easygoing about variable

types, but you can make a variable act like a Boolean simply by assigning it only

the values TRUEor FALSE In the fillBoard()function, look at how the $keepGoing

variable is used It is initialized to TRUE, and the function’s main loop keeps

run-ning as long as this is the case

However, the two conditions that can cause the loop to exit—the addWord()

func-tion failed to place a word correctly, or the entire word list has been exhausted—

cause the $keepGoingvariable to become FALSE When this happens, the loop stops

and the function shortly exits

function fillBoard(){

//fill board with list by calling addWord() for each word

//or return false if failed

global $word;

$direction = array(“N”, “S”, “E”, “W”);

$itWorked = TRUE;

$counter = 0;

$keepGoing = TRUE;

while($keepGoing){

$dir = rand(0, 3);

$result = addWord($word[$counter], $direction[$dir]);

if ($result = = FALSE){

167

l i

Ngày đăng: 07/07/2014, 02:20