This is Random.m in view mode; [Download] [Up]
// // Random // // <<See the file Random.h for more information>>. // // Version 1.0, 1991 May 30 // // Written by Gregor Purdy // gregor@oit.itd.umich.edu // // See the README and COPYING files included for // information and distribution and usage rights. // #import <sys/time.h> #import "Random.h" @implementation Random - init { [super init]; // Make a new instance using superclass' method [self newSeeds]; // Get a new seed for ourselves return self; } - initSeeds:(int)s1 :(int)s2 :(int)s3 { [super init]; [self setSeeds:s1 :s2 :s3]; return self; } - newSeeds { struct timeval theTime; // gettimeofday return structure gettimeofday(&theTime,0); // Get the time of day in seconds and microseconds h1 = theTime.tv_usec; // Set seed 1 by microseconds past second gettimeofday(&theTime,0); // Get the time of day in seconds and microseconds h2 = theTime.tv_usec; // Set seed 2 by microseconds past second gettimeofday(&theTime,0); // Get the time of day in seconds and microseconds h3 = theTime.tv_usec; // Set seed 3 by microseconds past second return self; } - setSeeds:(int) s1 :(int) s2 :(int) s3 { h1 = s1; // Set the seeds to the values given h2 = s2; h3 = s3; return self; } - getSeeds:(int *)s1 :(int *)s2 :(int *)s3 { if((s1 == NULL) || (s2 == NULL) || (s3 == NULL)) return nil; *s1 = h1; *s2 = h2; *s3 = h3; return self; } // // See the Source article for the explanations of these constants // #define M1 32771 #define M2 32779 #define M3 32783 #define F1 179 #define F2 183 #define F3 182 #define MAXNUM 32767 #define RANGE 32768 - (int) rand { h1 = (F1 * h1) % M1; // Update the sections h2 = (F2 * h2) % M2; h3 = (F2 * h3) % M3; if ((h1 > MAXNUM) || (h2 > MAXNUM) || (h3 > MAXNUM)) // If a section is out of range, return [self rand]; // return next result else // Otherwise, return (h1 + h2 + h3) % RANGE; // Return this result } - (int) randMax:(int)max { return (int)((float)[self rand] / (float)RANGE * (float)(max + 1)); } - (int) randMin:(int)min max:(int)max { return min + [self randMax:(max - min)]; } - (float) percent { return ((float)[self rand] / (float)RANGE); } - (int) rollDie:(int) numSides { return [self randMax:(numSides - 1)] + 1; } - (int) roll:(int) numRolls die:(int) numSides { int temp = 0; int loop; for (loop = 1 ; loop <= numRolls ; loop++ ) temp += [self rollDie:numSides]; return temp; } - (int) rollBest:(int)numWanted of:(int)numRolls die:(int)numSides { int temp[numRolls]; // Array of rolls int loop1; // First loop control variable int loop2; // Second loop control variable int highest; // Index of highest found roll int accumulator = 0; // Accumulates total best roll for (loop1 = 1 ; loop1 <= numRolls ; loop1++) // Fill an array with rolls temp[loop1] = [self rollDie:numSides]; for (loop1 = 1 ; loop1 <= numWanted; loop1++) { highest = 1; // Start off as if first is highest for (loop2 = 2 ; loop2 <= numRolls ; loop2++) // Scan array for higher rolls if (temp[loop2] > temp[highest]) // If temp[loop2] is higher, then highest = loop2; // remember that fact accumulator += temp[highest]; // Add highest roll to accumulator temp[highest] = 0; // Clear highest roll so we don't find it again } return accumulator; // Return what we found } - read:(NXTypedStream *)stream { [super read:stream]; NXReadTypes(stream, "iii", &h1, &h2, &h3); return self; } - write:(NXTypedStream *)stream { [super write:stream]; NXWriteTypes(stream, "iii", &h1, &h2, &h3); return self; } @end // // End of file. //
These are the contents of the former NiCE NeXT User Group NeXTSTEP/OpenStep software archive, currently hosted by Netfuture.ch.