Adding items in a list randomly 100 times in Python - random

Hey all I just started learning about programming and this is problem I need to solve but I just can't get it:
Get your computer to produce its 100 first utterances. These utterances are sequences of 1, 2, 3,
or 4 random syllables sampled from the list:
[“ba”,”bi”,”bu”,”ga”,”gi”,”gu”].
You have to write a program that prints 100 random utterances of this type. For each utterances you have to select a random length (of 1, 2,3 or 4 syllables) for each utterance, plus randomly sample the chosen number of syllables from the set above.

So there's no point just giving you code, or you won't learn anything, but here are some ingredients:
You'll want a for loop that runs 100 times to give 100 utterances.
Inside that loop, you need a random number from 1 to 4 (for the number of syllables). You could import the random module and use randint to get the number. Let's say you call this number n_syll. Also, initialize an empty string to hold your word.
Then, still inside the original for loop, you need to make the actual word. Start another for loop that runs n_syll times. On each iteration, randomly select the syllable (see How to randomly select an item from a list?). Concatenate it with the word string.
When you pop outside the inner loop, you should have a random word. Just print it!
This isn't the most elegant way to do it, but it'll get the job done.
If any of these steps are too hard, maybe run through the Codecademy Python tutorial to get familiar with the basics of the language.

Related

Yahtzee 3 of a Kind

Here is my situation, i am currently creating a Yahtzee game using Turbo Pascal Language in Lazarus IDE and i am up to the scoring side of the developement, i have already completed the Lower section of scoring and i have started the Higher section but i need some help writting a procedure to check for a three of a kind, my initial thought was to use an array and load the random numbers for the dice values and then use a loop function to check for 3 equal numbers but i'm not very confident in this area. Could i get some help ? I'm not asking for code, although it would be helpful, just a push in the right direction.
My dice integer value variables are, "Dice1" , "Dice2" , "Dice3" , "Dice4" , "Dice5" , "Dice6"
I think the conceptually simplest approach is to have an array of six counters - one for each possible value - that you initialize to zero and then loop over your dice array and increment the counters with each die's value.
You can then check if any of the counts becomes 3 (or more).
Or sort and then iterate to see if you have 3 same values in a row. The sorted array with dice values is also usable for the other detections like street, Carré (four of a kind), Yathzee etc.

Ifinstring: locate variable number after text then randomly Send new number +/- 20 of that #

I have a very simple AHK script that reads a log.txt every so often and then randomly generates numbers within a range when the triggering text is found then Sends the random number as my guess. It's for a stupid lottery type thing.
The thing is, if the previous winning number was, for instance, 40, then it's seemingly never within 20 numbers of 40 again the next time around, so I'm trying to figure out how to locate the number 40 immediately after my Ifinstring trigger, then randomly generate (and then Send,) a single number between 0 and 20 as well as 60 to 100. I'm sure there's plenty of efficient ways to do this but I'm new and would like a simple way. It's just a macro really, and I'm just a newbie trying to optimize my one script.
Thanks for the patience and help :)

Generating Bulls and Cows secret word with given n String inputs

I am stuck on this problem for quite a while, it is basically reverse engineering bulls and cow game.
Read more here: http://rosettacode.org/wiki/Bulls_and_cows
I am not able to develop a logic for the problem given below, if you can think of a solving approach please comment the same.
Problem Statement:
Given few clue words(of form ABCD/DBCA etc) and the number of cows and bulls for each word,program
should be able to work out the actual word by evaluating the given clue words and generate the output secret word.
TEST CASES:
Input:
4
DBCC 0 2
CDAB 2 1
CAAD 1 2
CDDA 2 0
Output:
BDAA
The idea is to reduce the space of possible solutions. Before you start, all 4^4 combinations are possible. After you read the first clue [DBCC 0 2 ], you can eliminate a number of possible solutions, in this particular example you can eliminate all states which have a D in the first place, all which have a B in the second place and so on. Just eliminate all possible solutions which do not "fit" the current clue.
Do this with each clue, until only one solution is left. Another interesting problem of course is how to generate good clue patterns.
The way I did it is:
1. Generate all possible words, put them in a list (array)
2. Randomly select one of them (first question)and ask for clues
3. Take the answer (let's say it is 2,1)
4. Start comparing that question with
first, second, ..., to the last word from the list
5. if they give the same clue: count them, plac

Need some help with a dice rolling algorithm

How would I go about pseudocoding the algorithm for a method that:
Rolls a type of Die - 4 , 6 , 8 , 10 , or 12 sided
Can roll up to ten of this type of Die
If more than half of the die are 1's, print them a message that they bust and end the program
If any of the die are equal to the type of die rolled, take the highest value from the group. As well as re-roll the die that equaled the value of the type of die rolled.
^^^^I.E. - Let's say you have 3 six sided die, you roll them and you get a 4, 2 and 6. You take the value of 6, since it is the highest. Then you re-roll the die that was a six. If you get a six you add that six to the previous six AND re-roll. If not you just add the highest die there to the previous value.
I think your question points to the reason you are finding this difficult. You are trying to solve too much in one place and that becomes overwhelming. You don't want to create a single method to do that. You will want to create several. Start by decomposing the problem into it's constituent parts.
Note: I'm not approaching this in an OO fashion to make the answer a bit easier to parse. I would encourage you to think about the design in more detail.
Requirement 1: Rolls a type of Die - 4 , 6 , 8 , 10 , or 12 sided
Ok - so we need some method similar to:
int Roll(int sides);
Basically Roll just returns a random value between 1 and sides (inclusive).
Requirement 2: Can roll up to ten of this type of Die
This would likely be a for loop.
Requirement 3: If more than half of the die are 1's, print them a message that they bust and end the program
This requirement implies that you are storing the results of each call to Roll in a collection - e.g., a List or an int[] (array of integers).
Next it says that you are iterating over that collection and counting the number of rolls that are "1". If count is greater than half the total number of rolls than you end the program. Counting is easy (for loop or foreach would probably be your best bet) and you know how many rolls were made (both by the number of items in the collection and because you had a counter on your for loop when the rolls were made ... so divide and compare.
Requirement 4: If any of the die are equal to the type of die rolled, take the highest value from the group. As well as re-roll the die that equaled the value of the type of die rolled.
Again - you need to iterate over the result set and perform the operation request. I would not attempt to "optimize" your solution by combining this rule with the previous rule - it will just convolute the solution for no real benefit.
Your algorithm would have to:
Roll the dice
Check the results to see if half are 1s
Check and possibly re-roll high numbers
Keep track of the accepted numbers and running totals from the rolled dice
There is not much more to it then to actually do it for you.

Best way to generate order numbers for an online store?

Every order in my online store has a user-facing order number. I'm wondering the best way to generate them. Criteria include:
Short
Easy to say over the phone (e.g., "m" and "n" are ambiguous)
Unique
Checksum (overkill? Useful?)
Edit: Doesn't reveal how many total orders there have been (a customer might find it unnerving to make your 3rd order)
Right now I'm using the following method (no checksum):
def generate_number
possible_values = 'abfhijlqrstuxy'.upcase.split('') | '123456789'.split('')
record = true
while record
random = Array.new(5){possible_values[rand(possible_values.size)]}.join
record = Order.find(:first, :conditions => ["number = ?", random])
end
self.number = random
end
As a customer I would be happy with:
year-month-day/short_uid
for example:
2009-07-27/KT1E
It gives room for about 33^4 ~ 1mln orders a day.
Here is an implementation for a system I proposed in an earlier question:
MAGIC = [];
29.downto(0) {|i| MAGIC << 839712541[i]}
def convert(num)
order = 0
0.upto(MAGIC.length - 1) {|i| order = order << 1 | (num[i] ^ MAGIC[i]) }
order
end
It's just a cheap hash function, but it makes it difficult for an average user to determine how many orders have been processed, or a number for another order. It won't run out of space until you've done 230 orders, which you won't hit any time soon.
Here are the results of convert(x) for 1 through 10:
1: 302841629
2: 571277085
3: 34406173
4: 973930269
5: 437059357
6: 705494813
7: 168623901
8: 906821405
9: 369950493
10: 638385949
At my old place it was the following:
The customer ID (which started at 1001), the sequence of the order they made then the unique ID from the Orders table. That gave us a nice long number of at least 6 digits and it was unique because of the two primary keys.
I suppose if you put dashes or spaces in you could even get us a little insight into the customer's purchasing habits. It isn't mind boggling secure and I guess a order ID would be guessable but I am not sure if there is security risk in that or not.
Ok, how about this one?
Sequentially, starting at some number (2468) and add some other number to it, say the day of the month that the order was placed.
The number always increases (until you exceed the capacity of the integer type, but by then you probably don't care, as you will be incredibly successful and will be sipping margaritas in some far-off island paradise). It's simple enough to implement, and it mixes things up enough to throw off any guessing as to how many orders you have.
I'd rather submit the number 347 and get great customer service at a smaller personable website than: G-84e38wRD-45OM at the mega-site and be ignored for a week.
You would not want this as a system id or part of a link, but as a user-friendly number it works.
Douglas Crockford's Base32 Encoding works superbly well for this.
http://www.crockford.com/wrmg/base32.html
Store the ID itself in your database as an auto-incrementing integer, starting at something suitably large like 100000, and simply expose the encoded value to the customer/interface.
5 characters will see you through your first ~32 million orders, whilst performing very well and satisfying most of these requirements. It doesn't allow for the exclusion of similar sounding characters though.
Rather than generating and storing a number, you might try creating an encrypted version that would not reveal the number of orders in the system. Here's an article on exactly that.
Something like this:
Get sequential order number. Or, maybe, an UNIX timestamp plus two or three random digits (when two orders are placed at the same moment) is fine too.
Bitwise-XOR it with some semi-secret value to make number appear "pseudo-random". This is primitive and won't stop those who really want to investigate how many orders you have, but for true "randomness" you need to keep a (large) permutation table. Or you'll need to have large random numbers, so you won't be hit by the birthday paradox.
Add checkdigit using Verhoeff algorithm (I'm not sure it will have such a good properties for base33, but it shouldn't be bad).
Convert the number to - for example - base 33 ("0-9A-Z", except for "O", "Q" and "L" which can be mistaken with "0" and "1") or something like that. Ease of pronouncation means excluding more letters.
Group the result in some visually readable pattern, like XXX-XXX-XX, so users won't have to track the position with their fingers or mouse pointers.
Sequentially, starting at 1? What's wrong with that?
(Note: This answer was given before the OP edited the question.)
Just one Rube Goldberg-style idea:
You could generate a table with a random set of numbers that is tied to a random period of time:
Time Period Interleaver
next 2 weeks: 442
following 8 days: 142
following 3 weeks: 580
and so on... this gives you an unlimited number of Interleavers, and doesn't let anyone know your rate of orders because your time periods could be on the order of days and your interleaver is doing a lot of low-tech "mashing" for you.
You can generate this table once, and simply ensure that all Interleavers are unique.
You can ensure you don't run out of Interleavers by simply adding more characters into the set, or start by defining longer Interleavers.
So you generate an order ID by getting a sequential number, and using today's Interleaver value, interleave its digits (hence, the name) in between each sequential number's digits. Guaranteed unique - guaranteed confusing.
Example:
Today I have a sequential number 1, so I will generate the order ID: 4412
The next order will be 4422
The next order will be 4432
The 10th order will be 41402
In two weeks my interleaver will change to 142,
The 200th order will be 210402
The 201th order will be 210412
Eight days later, my interleaver changes to 580:
The 292th order will be 259820
This will be completely confusing but completely deterministic. You can just remove every other digit starting at the 1's place. (except when your order id is only one digit longer than your interleaver)
I didn't say this was the best way - just a Friday idea.
You could do it like a postal code:
2b2 b2b
That way it has some kind of checksum (not really, but at least you know it's wrong if there are 2 consecutive numbers or letters). It's easy to read out over the phone, and it doesn't give an indication of how many orders are in the system.
http://blog.logeek.fr/2009/7/2/creating-small-unique-tokens-in-ruby
>> rand(36**8).to_s(36)
=> "uur0cj2h"
How about getting the current time in miliseconds and using that as your order ID?

Resources