mirror of
https://github.com/caperren/school_archives.git
synced 2025-11-09 21:51:15 +00:00
Added Software Engineering II code
This commit is contained in:
@@ -0,0 +1,60 @@
|
||||
#############################
|
||||
########## Bug #01 ##########
|
||||
#############################
|
||||
Title: playSmithy Incorrect Card Pickup Count
|
||||
|
||||
Affected Files: dominion.c
|
||||
|
||||
Pertinent Code:
|
||||
dominion.c: Line 717
|
||||
|
||||
Test Environment: Red Hat Linux 4.8.5-4 (Kernel 3.10.0)
|
||||
|
||||
Expected Result:
|
||||
A call to playSmithy should add three cards to the player's hand, then
|
||||
discard the played card. The final result should be a hand with two extra cards
|
||||
in it.
|
||||
|
||||
Actual Result:
|
||||
playSmithy picks up five cards instead of three, then discards a card like
|
||||
normal. The result is a hand with four extra cards instead of two.
|
||||
|
||||
Steps to Reproduce:
|
||||
1. Use the other game functions to set up a normal game state.
|
||||
2. Set a current player.
|
||||
3. Save the handcount for the player in a temp variable.
|
||||
4. Call playSmithy against the selected player.
|
||||
5. Compare the saved handcount to the new handcount to see incorrect number.
|
||||
|
||||
|
||||
#############################
|
||||
########## Bug #02 ##########
|
||||
#############################
|
||||
Title: playAdventurer Incorrect Hand Count When Drawing Non-Treasure Cards
|
||||
|
||||
Affected Files: dominion.c
|
||||
|
||||
Pertinent Code:
|
||||
dominion.c: Line 701
|
||||
|
||||
Test Environment: Red Hat Linux 4.8.5-4 (Kernel 3.10.0)
|
||||
|
||||
Expected Result:
|
||||
In a call to playAdventurer, during the process of "picking up" cards,
|
||||
the temp hand stores a copy of any cards that aren't treasure cards, then
|
||||
removes the just saved "top card". This allows cards to be shuffled back into
|
||||
the game without being lost.
|
||||
|
||||
Actual Result:
|
||||
In a call to playAdventurer, during the process of "picking up" cards,
|
||||
instead of removing the top card, an invalid top card is instead added.
|
||||
Depending on the previous state of the hand, the error may not show itself,
|
||||
for example, if every card picked up were a treasure card. In the case where
|
||||
this bug is hit, invalid cards could be shuffled back into the players hand at
|
||||
a later time, causing major bugs in gameplay.
|
||||
|
||||
Steps to Reproduce:
|
||||
1. Use the other game functions to set up a normal game state.
|
||||
2. Set a current player.
|
||||
4. Call playAdventurer against the selected player.
|
||||
5. Manually inspect the hand of the player and note invalid card indexes.
|
||||
@@ -0,0 +1,27 @@
|
||||
CFLAGS = -Wall -fpic -coverage -lm -std=c99 -ftest-coverage -fprofile-arcs
|
||||
|
||||
all: assignment5
|
||||
|
||||
assignment5:
|
||||
echo "Compiling and running all tests....." > unittestresults.out
|
||||
|
||||
gcc -o cardtest2 cardtest2.c dominion.c rngs.c -g $(CFLAGS)
|
||||
echo "Running Cardtest2...." >> unittestresults.out
|
||||
./cardtest2 >> unittestresults.out
|
||||
gcov dominion.c >> unittestresults.out
|
||||
cat dominion.c.gcov >> unittestresults.out
|
||||
cat dominion.c.gcov >> cardtest2.gcov
|
||||
|
||||
echo "######################################" >> unittestresults.out
|
||||
echo "######################################" >> unittestresults.out
|
||||
|
||||
gcc -o cardtest3 cardtest3.c dominion.c rngs.c -g $(CFLAGS)
|
||||
echo "Running Cardtest3...." >> unittestresults.out
|
||||
./cardtest3 >> unittestresults.out
|
||||
gcov dominion.c >> unittestresults.out
|
||||
cat dominion.c.gcov >> unittestresults.out
|
||||
cat dominion.c.gcov >> cardtest3.gcov
|
||||
|
||||
clean:
|
||||
rm -f *.o playdom.exe playdom test.exe test player player.exe testInit testInit.exe *.gcov *.gcda *.gcno *.so *.out
|
||||
rm -f cardtest2 cardtest3
|
||||
@@ -0,0 +1,85 @@
|
||||
/*
|
||||
* To change this license header, choose License Headers in Project Properties.
|
||||
* To change this template file, choose Tools | Templates
|
||||
* and open the template in the editor.
|
||||
*/
|
||||
|
||||
/*
|
||||
* File: unittest1.c
|
||||
* Author: corwinperren
|
||||
*
|
||||
* Created on February 1, 2017, 9:02 PM
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include "dominion.h"
|
||||
#include "dominion_helpers.h"
|
||||
#include "rngs.h"
|
||||
|
||||
int testing_assert(int expression, int should_print);
|
||||
|
||||
long sucesses = 0;
|
||||
long failures = 0;
|
||||
|
||||
int main(int argc, char** argv) {
|
||||
struct gameState G, G_copy;
|
||||
int k[10] = {adventurer, gardens, embargo, village, minion, mine, cutpurse,
|
||||
sea_hag, tribute, smithy};
|
||||
|
||||
|
||||
unsigned int arbitrary_hand_count_max = MAX_HAND - 3;
|
||||
|
||||
for(int l = 0 ; l < 4 ; l++){
|
||||
for(int i = 1 ; i < arbitrary_hand_count_max ; i++){
|
||||
initializeGame(4, k, 65432, &G);
|
||||
G.handCount[0] = arbitrary_hand_count_max;
|
||||
G.whoseTurn = l;
|
||||
|
||||
G_copy = G;
|
||||
|
||||
drawCard(0, &G_copy);
|
||||
drawCard(0, &G_copy);
|
||||
drawCard(0, &G_copy);
|
||||
discardCard(i, l, &G_copy, 0);
|
||||
|
||||
playSmithy(&G, i, G.whoseTurn);
|
||||
|
||||
testing_assert(G.handCount[l] == G_copy.handCount[l], 0);
|
||||
|
||||
for(int j = 0 ; j < arbitrary_hand_count_max ; j++){
|
||||
testing_assert((G.hand[l][j] >= curse) && (G.hand[l][j] <= treasure_map), 0);
|
||||
testing_assert((G_copy.hand[l][j] >= curse) && (G_copy.hand[l][j] <= treasure_map), 0);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
printf("Run complete!\n");
|
||||
printf("SUCCESSES: %ld\n", sucesses);
|
||||
|
||||
if(failures > 0){
|
||||
printf("Some tests failed!!!\n");
|
||||
printf("FAILURES: %ld\n", failures);
|
||||
}
|
||||
|
||||
return (EXIT_SUCCESS);
|
||||
}
|
||||
|
||||
int testing_assert(int expression, int should_print) {
|
||||
if (expression) {
|
||||
if(should_print){
|
||||
printf("TEST SUCCEEDED!\n");
|
||||
}
|
||||
sucesses++;
|
||||
return 1;
|
||||
} else {
|
||||
if(should_print){
|
||||
printf("TEST FAILED!\n");
|
||||
}
|
||||
failures++;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,92 @@
|
||||
/*
|
||||
* To change this license header, choose License Headers in Project Properties.
|
||||
* To change this template file, choose Tools | Templates
|
||||
* and open the template in the editor.
|
||||
*/
|
||||
|
||||
/*
|
||||
* File: unittest1.c
|
||||
* Author: corwinperren
|
||||
*
|
||||
* Created on February 1, 2017, 9:02 PM
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include "dominion.h"
|
||||
#include "dominion_helpers.h"
|
||||
#include "rngs.h"
|
||||
|
||||
int testing_assert(int expression, int should_print);
|
||||
|
||||
long sucesses = 0;
|
||||
long failures = 0;
|
||||
|
||||
int main(int argc, char** argv) {
|
||||
struct gameState G;
|
||||
int k[10] = {adventurer, gardens, embargo, village, minion, mine, cutpurse,
|
||||
sea_hag, tribute, smithy};
|
||||
|
||||
unsigned int arbitrary_hand_count_max = MAX_HAND - 2;
|
||||
|
||||
for(int l = 0 ; l < 4 ; l++){
|
||||
for(int i = 1 ; i < arbitrary_hand_count_max ; i++){
|
||||
initializeGame(4, k, 65432, &G);
|
||||
G.handCount[l] = arbitrary_hand_count_max;
|
||||
G.whoseTurn = l;
|
||||
|
||||
int temp_hand[MAX_HAND];
|
||||
playAdventurer(0, &G, G.whoseTurn, temp_hand, 0);
|
||||
|
||||
testing_assert(G.handCount[l] == arbitrary_hand_count_max + 2, 0);
|
||||
testing_assert((G.hand[l][G.handCount[l] - 1] >= copper) && (G.hand[l][G.handCount[l] - 1] <= gold), 0);
|
||||
testing_assert((G.hand[l][G.handCount[l] - 2] >= copper) && (G.hand[l][G.handCount[l] - 2] <= gold), 0);
|
||||
|
||||
initializeGame(4, k, 65432, &G);
|
||||
G.handCount[l] = arbitrary_hand_count_max;
|
||||
G.whoseTurn = l;
|
||||
G.deckCount[l] = 0;
|
||||
|
||||
for(int m = 0 ; m < MAX_DECK ; m += 3){
|
||||
G.discard[l][m] = copper;
|
||||
G.discard[l][m + 1] = silver;
|
||||
G.discard[l][m + 2] = gold;
|
||||
G.discardCount[l] += 3;
|
||||
}
|
||||
|
||||
playAdventurer(0, &G, G.whoseTurn, temp_hand, 0);
|
||||
|
||||
testing_assert(G.handCount[l] == arbitrary_hand_count_max + 2, 0);
|
||||
testing_assert((G.hand[l][G.handCount[l] - 1] >= copper) && (G.hand[l][G.handCount[l] - 1] <= gold), 0);
|
||||
testing_assert((G.hand[l][G.handCount[l] - 2] >= copper) && (G.hand[l][G.handCount[l] - 2] <= gold), 0);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
printf("Run complete!\n");
|
||||
printf("SUCCESSES: %ld\n", sucesses);
|
||||
|
||||
if(failures > 0){
|
||||
printf("Some tests failed!!!\n");
|
||||
printf("FAILURES: %ld\n", failures);
|
||||
}
|
||||
|
||||
return (EXIT_SUCCESS);
|
||||
}
|
||||
|
||||
int testing_assert(int expression, int should_print) {
|
||||
if (expression) {
|
||||
if(should_print){
|
||||
printf("TEST SUCCEEDED!\n");
|
||||
}
|
||||
sucesses++;
|
||||
return 1;
|
||||
} else {
|
||||
if(should_print){
|
||||
printf("TEST FAILED!\n");
|
||||
}
|
||||
failures++;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,143 @@
|
||||
#ifndef _DOMINION_H
|
||||
#define _DOMINION_H
|
||||
|
||||
// Code from various sources, baseline from Kristen Bartosz
|
||||
|
||||
#define MAX_HAND 500
|
||||
#define MAX_DECK 500
|
||||
|
||||
#define MAX_PLAYERS 4
|
||||
|
||||
#define DEBUG 0
|
||||
|
||||
|
||||
|
||||
/* http://dominion.diehrstraits.com has card texts */
|
||||
/* http://dominion.isotropic.org has other stuff */
|
||||
|
||||
/* hand# means index of a card in current active player's hand */
|
||||
|
||||
enum CARD
|
||||
{curse = 0,
|
||||
estate, //1
|
||||
duchy, //2
|
||||
province, //3
|
||||
|
||||
copper, //4
|
||||
silver, //5
|
||||
gold, //6
|
||||
|
||||
adventurer, //7
|
||||
/* If no/only 1 treasure found, stop when full deck seen */
|
||||
council_room, //8
|
||||
feast, //9 /* choice1 is supply # of card gained) */
|
||||
gardens, //10
|
||||
mine, //11 /* choice1 is hand# of money to trash, choice2 is supply# of
|
||||
//money to put in hand */
|
||||
remodel, //12 /* choice1 is hand# of card to remodel, choice2 is supply# */
|
||||
smithy, //13
|
||||
village, //14
|
||||
|
||||
baron, //15 /* choice1: boolean for discard of estate */
|
||||
/* Discard is always of first (lowest index) estate */
|
||||
great_hall, //16
|
||||
minion, //17 /* choice1: 1 = +2 coin, 2 = redraw */
|
||||
steward, //18 /* choice1: 1 = +2 card, 2 = +2 coin, 3 = trash 2 (choice2,3) */
|
||||
tribute, //19
|
||||
|
||||
ambassador, //20 /* choice1 = hand#, choice2 = number to return to supply */
|
||||
cutpurse, //21
|
||||
embargo, //22 /* choice1 = supply# */
|
||||
outpost, //23
|
||||
salvager, //24 /* choice1 = hand# to trash */
|
||||
sea_hag, //25
|
||||
treasure_map //26
|
||||
};
|
||||
|
||||
struct gameState {
|
||||
int numPlayers; //number of players
|
||||
int supplyCount[treasure_map+1]; //this is the amount of a specific type of card given a specific number.
|
||||
int embargoTokens[treasure_map+1];
|
||||
int outpostPlayed;
|
||||
int outpostTurn;
|
||||
int whoseTurn;
|
||||
int phase;
|
||||
int numActions; /* Starts at 1 each turn */
|
||||
int coins; /* Use as you see fit! */
|
||||
int numBuys; /* Starts at 1 each turn */
|
||||
int hand[MAX_PLAYERS][MAX_HAND];
|
||||
int handCount[MAX_PLAYERS];
|
||||
int deck[MAX_PLAYERS][MAX_DECK];
|
||||
int deckCount[MAX_PLAYERS];
|
||||
int discard[MAX_PLAYERS][MAX_DECK];
|
||||
int discardCount[MAX_PLAYERS];
|
||||
int playedCards[MAX_DECK];
|
||||
int playedCardCount;
|
||||
};
|
||||
|
||||
/* All functions return -1 on failure, and DO NOT CHANGE GAME STATE;
|
||||
unless specified for other return, return 0 on success */
|
||||
|
||||
struct gameState* newGame();
|
||||
|
||||
int* kingdomCards(int k1, int k2, int k3, int k4, int k5, int k6, int k7,
|
||||
int k8, int k9, int k10);
|
||||
|
||||
int initializeGame(int numPlayers, int kingdomCards[10], int randomSeed,
|
||||
struct gameState *state);
|
||||
/* Responsible for initializing all supplies, and shuffling deck and
|
||||
drawing starting hands for all players. Check that 10 cards selected
|
||||
are in fact (different) kingdom cards, and that numPlayers is valid.
|
||||
|
||||
Cards not in game should initialize supply position to -1 */
|
||||
|
||||
int shuffle(int player, struct gameState *state);
|
||||
/* Assumes all cards are now in deck array (or hand/played): discard is
|
||||
empty */
|
||||
|
||||
int playCard(int handPos, int choice1, int choice2, int choice3,
|
||||
struct gameState *state);
|
||||
/* Play card with index handPos from current player's hand */
|
||||
|
||||
int buyCard(int supplyPos, struct gameState *state);
|
||||
/* Buy card with supply index supplyPos */
|
||||
|
||||
int numHandCards(struct gameState *state);
|
||||
/* How many cards current player has in hand */
|
||||
|
||||
int handCard(int handNum, struct gameState *state);
|
||||
/* enum value of indexed card in player's hand */
|
||||
|
||||
int supplyCount(int card, struct gameState *state);
|
||||
/* How many of given card are left in supply */
|
||||
|
||||
int fullDeckCount(int player, int card, struct gameState *state);
|
||||
/* Here deck = hand + discard + deck */
|
||||
|
||||
int whoseTurn(struct gameState *state);
|
||||
|
||||
int endTurn(struct gameState *state);
|
||||
/* Must do phase C and advance to next player; do not advance whose turn
|
||||
if game is over */
|
||||
|
||||
int isGameOver(struct gameState *state);
|
||||
|
||||
int scoreFor(int player, struct gameState *state);
|
||||
/* Negative here does not mean invalid; scores may be negative,
|
||||
-9999 means invalid input */
|
||||
|
||||
int getWinners(int players[MAX_PLAYERS], struct gameState *state);
|
||||
/* Set array position of each player who won (remember ties!) to
|
||||
1, others to 0 */
|
||||
|
||||
/*int playAdventurer(struct gameState *state);
|
||||
int playSmithy(struct gameState *state, int handPos);
|
||||
int playVillage(struct gameState *state, int handPos);
|
||||
int playFeast(struct gameState *state, int choice1);
|
||||
int playCouncil_Room(struct gameState *state, int handPos);*/
|
||||
|
||||
int playAdventurer(int drawntreasure, struct gameState *state, int currentPlayer, int temphand[MAX_HAND], int z);
|
||||
int playSmithy(struct gameState *state, int handPos, int currentPlayer);
|
||||
int playVillage(int currentPlayer, struct gameState *state, int handPos);
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,15 @@
|
||||
#ifndef _DOMINION_HELPERS_H
|
||||
#define _DOMINION_HELPERS_H
|
||||
|
||||
#include "dominion.h"
|
||||
|
||||
int drawCard(int player, struct gameState *state);
|
||||
int updateCoins(int player, struct gameState *state, int bonus);
|
||||
int discardCard(int handPos, int currentPlayer, struct gameState *state,
|
||||
int trashFlag);
|
||||
int gainCard(int supplyPos, struct gameState *state, int toFlag, int player);
|
||||
int getCost(int cardNumber);
|
||||
int cardEffect(int card, int choice1, int choice2, int choice3,
|
||||
struct gameState *state, int handPos, int *bonus);
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,179 @@
|
||||
/* -------------------------------------------------------------------------
|
||||
* This is an ANSI C library for multi-stream random number generation.
|
||||
* The use of this library is recommended as a replacement for the ANSI C
|
||||
* rand() and srand() functions, particularly in simulation applications
|
||||
* where the statistical 'goodness' of the random number generator is
|
||||
* important. The library supplies 256 streams of random numbers; use
|
||||
* SelectStream(s) to switch between streams indexed s = 0,1,...,255.
|
||||
*
|
||||
* The streams must be initialized. The recommended way to do this is by
|
||||
* using the function PlantSeeds(x) with the value of x used to initialize
|
||||
* the default stream and all other streams initialized automatically with
|
||||
* values dependent on the value of x. The following convention is used
|
||||
* to initialize the default stream:
|
||||
* if x > 0 then x is the state
|
||||
* if x < 0 then the state is obtained from the system clock
|
||||
* if x = 0 then the state is to be supplied interactively.
|
||||
*
|
||||
* The generator used in this library is a so-called 'Lehmer random number
|
||||
* generator' which returns a pseudo-random number uniformly distributed
|
||||
* 0.0 and 1.0. The period is (m - 1) where m = 2,147,483,647 and the
|
||||
* smallest and largest possible values are (1 / m) and 1 - (1 / m)
|
||||
* respectively. For more details see:
|
||||
*
|
||||
* "Random Number Generators: Good Ones Are Hard To Find"
|
||||
* Steve Park and Keith Miller
|
||||
* Communications of the ACM, October 1988
|
||||
*
|
||||
* Name : rngs.c (Random Number Generation - Multiple Streams)
|
||||
* Authors : Steve Park & Dave Geyer
|
||||
* Language : ANSI C
|
||||
* Latest Revision : 09-22-98
|
||||
* -------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <time.h>
|
||||
#include "rngs.h"
|
||||
|
||||
#define MODULUS 2147483647 /* DON'T CHANGE THIS VALUE */
|
||||
#define MULTIPLIER 48271 /* DON'T CHANGE THIS VALUE */
|
||||
#define CHECK 399268537 /* DON'T CHANGE THIS VALUE */
|
||||
#define STREAMS 256 /* # of streams, DON'T CHANGE THIS VALUE */
|
||||
#define A256 22925 /* jump multiplier, DON'T CHANGE THIS VALUE */
|
||||
#define DEFAULT 123456789 /* initial seed, use 0 < DEFAULT < MODULUS */
|
||||
|
||||
static long seed[STREAMS] = {DEFAULT}; /* current state of each stream */
|
||||
static int stream = 0; /* stream index, 0 is the default */
|
||||
static int initialized = 0; /* test for stream initialization */
|
||||
|
||||
|
||||
double Random(void)
|
||||
/* ----------------------------------------------------------------
|
||||
* Random returns a pseudo-random real number uniformly distributed
|
||||
* between 0.0 and 1.0.
|
||||
* ----------------------------------------------------------------
|
||||
*/
|
||||
{
|
||||
const long Q = MODULUS / MULTIPLIER;
|
||||
const long R = MODULUS % MULTIPLIER;
|
||||
long t;
|
||||
|
||||
t = MULTIPLIER * (seed[stream] % Q) - R * (seed[stream] / Q);
|
||||
if (t > 0)
|
||||
seed[stream] = t;
|
||||
else
|
||||
seed[stream] = t + MODULUS;
|
||||
return ((double) seed[stream] / MODULUS);
|
||||
}
|
||||
|
||||
|
||||
void PlantSeeds(long x)
|
||||
/* ---------------------------------------------------------------------
|
||||
* Use this function to set the state of all the random number generator
|
||||
* streams by "planting" a sequence of states (seeds), one per stream,
|
||||
* with all states dictated by the state of the default stream.
|
||||
* The sequence of planted states is separated one from the next by
|
||||
* 8,367,782 calls to Random().
|
||||
* ---------------------------------------------------------------------
|
||||
*/
|
||||
{
|
||||
const long Q = MODULUS / A256;
|
||||
const long R = MODULUS % A256;
|
||||
int j;
|
||||
int s;
|
||||
|
||||
initialized = 1;
|
||||
s = stream; /* remember the current stream */
|
||||
SelectStream(0); /* change to stream 0 */
|
||||
PutSeed(x); /* set seed[0] */
|
||||
stream = s; /* reset the current stream */
|
||||
for (j = 1; j < STREAMS; j++) {
|
||||
x = A256 * (seed[j - 1] % Q) - R * (seed[j - 1] / Q);
|
||||
if (x > 0)
|
||||
seed[j] = x;
|
||||
else
|
||||
seed[j] = x + MODULUS;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void PutSeed(long x)
|
||||
/* ---------------------------------------------------------------
|
||||
* Use this function to set the state of the current random number
|
||||
* generator stream according to the following conventions:
|
||||
* if x > 0 then x is the state (unless too large)
|
||||
* if x < 0 then the state is obtained from the system clock
|
||||
* if x = 0 then the state is to be supplied interactively
|
||||
* ---------------------------------------------------------------
|
||||
*/
|
||||
{
|
||||
char ok = 0;
|
||||
|
||||
if (x > 0)
|
||||
x = x % MODULUS; /* correct if x is too large */
|
||||
if (x < 0)
|
||||
x = ((unsigned long) time((time_t *) NULL)) % MODULUS;
|
||||
if (x == 0)
|
||||
while (!ok) {
|
||||
printf("\nEnter a positive integer seed (9 digits or less) >> ");
|
||||
scanf("%ld", &x);
|
||||
ok = (0 < x) && (x < MODULUS);
|
||||
if (!ok)
|
||||
printf("\nInput out of range ... try again\n");
|
||||
}
|
||||
seed[stream] = x;
|
||||
}
|
||||
|
||||
|
||||
void GetSeed(long *x)
|
||||
/* ---------------------------------------------------------------
|
||||
* Use this function to get the state of the current random number
|
||||
* generator stream.
|
||||
* ---------------------------------------------------------------
|
||||
*/
|
||||
{
|
||||
*x = seed[stream];
|
||||
}
|
||||
|
||||
|
||||
void SelectStream(int index)
|
||||
/* ------------------------------------------------------------------
|
||||
* Use this function to set the current random number generator
|
||||
* stream -- that stream from which the next random number will come.
|
||||
* ------------------------------------------------------------------
|
||||
*/
|
||||
{
|
||||
stream = ((unsigned int) index) % STREAMS;
|
||||
if ((initialized == 0) && (stream != 0)) /* protect against */
|
||||
PlantSeeds(DEFAULT); /* un-initialized streams */
|
||||
}
|
||||
|
||||
|
||||
void TestRandom(void)
|
||||
/* ------------------------------------------------------------------
|
||||
* Use this (optional) function to test for a correct implementation.
|
||||
* ------------------------------------------------------------------
|
||||
*/
|
||||
{
|
||||
long i;
|
||||
long x;
|
||||
/*double u;*/ /* used to be uncommented */
|
||||
char ok = 0;
|
||||
|
||||
SelectStream(0); /* select the default stream */
|
||||
PutSeed(1); /* and set the state to 1 */
|
||||
for(i = 0; i < 10000; i++)
|
||||
Random(); /* used to have u = Random() */
|
||||
GetSeed(&x); /* get the new state value */
|
||||
ok = (x == CHECK); /* and check for correctness */
|
||||
|
||||
SelectStream(1); /* select stream 1 */
|
||||
PlantSeeds(1); /* set the state of all streams */
|
||||
GetSeed(&x); /* get the state of stream 1 */
|
||||
ok = ok && (x == A256); /* x should be the jump multiplier */
|
||||
if (ok)
|
||||
printf("\n The implementation of rngs.c is correct.\n\n");
|
||||
else
|
||||
printf("\n\a ERROR -- the implementation of rngs.c is not correct.\n\n");
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
/* -----------------------------------------------------------------------
|
||||
* Name : rngs.h (header file for the library file rngs.c)
|
||||
* Author : Steve Park & Dave Geyer
|
||||
* Language : ANSI C
|
||||
* Latest Revision : 09-22-98
|
||||
* -----------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#if !defined( _RNGS_ )
|
||||
#define _RNGS_
|
||||
|
||||
double Random(void);
|
||||
void PlantSeeds(long x);
|
||||
void GetSeed(long *x);
|
||||
void PutSeed(long x);
|
||||
void SelectStream(int index);
|
||||
void TestRandom(void);
|
||||
|
||||
#endif
|
||||
Reference in New Issue
Block a user