Search Unity

Get a random word from the dictionary

Discussion in 'Scripting' started by Raelin_, Feb 3, 2016.

  1. Raelin_

    Raelin_

    Joined:
    Jul 16, 2014
    Posts:
    20
    I'm trying to make a game where you have to a minigame is where you have to type in the words it gives you. I want to be able to get a random word from the english dictionary with a set length. for example i could set the length of the string to 4 and it would only generate words with 4 letters etc. does anyone know where to begin with this? will i have to import a long list of words into a list or array or is there a way to generate from the dictionary?
     
  2. orb

    orb

    Joined:
    Nov 24, 2010
    Posts:
    3,037
    If you're importing dictionaries and sorting by word length, a series of arrays or lists is probably going to be the most efficient.

    Given a text file "English.txt" containing a word per line (stored in Resources), this is the first thing I'd do:
    Code (CSharp):
    1. TextAsset txt = (TextAsset)Resources.Load("English");
    2. string[] dict = txt.text.Split("\n"[0]); // Should probably check for null in txt, but it's just an example
    Create a dictionary of lists for different word lengths:
    Code (CSharp):
    1. Dictionary<int,List<string>> words = new Dictionary<int, List<string>>();
    2. for(int len = 3; len < 11; len++)
    3. {
    4.     words[len] = new List<string>();
    5. }
    In this example I'm only interested in words 3-10 letters long.

    Finally, add the words to the sub-dictionaries:
    Code (CSharp):
    1. foreach(string word in dict)
    2. {
    3.     int n = word.Length;
    4.     if(n < 11 && n > 2)
    5.     {
    6.         List<string> l = words[n];
    7.         l.Add(word);
    8.     }
    9. }
    Now use multidimensional access to words:
    Code (CSharp):
    1. string s = words[5][3];
    Straight-forward and naïve code, but it works :)
     
    idurvesh and Kiwasi like this.
  3. lordofduct

    lordofduct

    Joined:
    Oct 3, 2011
    Posts:
    8,532
    Honestly, if you want efficiency.

    I'd go with a simple sql file, with a single table of all words. The table contains columns for the word itself, another for length, maybe some more for category (noun, verb, adverb, etc), and any other columns for categorizing the words.

    Then you can just perform fast lookups for words by these categories, and you an even pull randoms.

    Code (csharp):
    1.  
    2. SELECT word FROM words WHERE word_len = 4 ORDER BY Rand() LIMIT 1
    3.  
    (my sql may be a little rusty, been writing aql for the past few years)

    I do believe database files already exist out there of the English dictionary already set up in similar ways. You might be able to integrate with an existing one. Otherwise you could write a one off program in Visual Studio that parsed a textfile into a db for you.

    It's funny to think, there used to be a day that the fundamental part of an operating system was its database...
     
  4. orb

    orb

    Joined:
    Nov 24, 2010
    Posts:
    3,037
    SQLite would probably be best for portability. Making a tool to stuff it with English words is quick and easy.
     
    lordofduct likes this.
  5. larku

    larku

    Joined:
    Mar 14, 2013
    Posts:
    1,422
    IMO this calls for the most simplistic solution as @orb suggests.

    I'm considering English here, so we're talking less than 65000 words which using the brute force sort above is likely to take sub second to perform and is very portable, and self contained.

    While SQL is good, I'm not sure I'd want to burden my app to an sql engine to store some words (that's some heavy weight lookup table :) )
     
  6. orb

    orb

    Joined:
    Nov 24, 2010
    Posts:
    3,037
    Well…my go-to dictionary has 265879 words ;)

    But yeah, it's a trade-off between lightweight code, fancy features and in-memory size. I have a DB-based word game prototype where I made an external tool to edit the word database, import dictionaries and set scores in an SQLite database. On the other hand, if you just need to load words and pick them at random, text will be fine.

    Exercise for the truly adventurous: Fiddling with Huffman tables and compression dictionaries to make a gzip-compressed word list with quick lookup time from a pre-made hash.
     
  7. Raelin_

    Raelin_

    Joined:
    Jul 16, 2014
    Posts:
    20
    Thanks everyone for all the replies, Im trying to use this method that you posted, im having a little trouble accessing the words that are generated from the Txt file. anytime I use the List words it shows up as red. im not sure if there I have to have a separate method for getting a random word from the list. sorry im a noob at coding.
     
  8. orb

    orb

    Joined:
    Nov 24, 2010
    Posts:
    3,037
    Yeah, that's because I forgot to specify what to include from the system libraries :p

    This'll be all you need at the top of the script(s) using Lists:
    Code (CSharp):
    1. using System.Collections.Generic;
    Have a look at the docs on MSDN to see what's in there, and which other Collections.* (or even System.*) classes could be useful. Remember that some aren't implemented in Unity's C# version (it's sort of 2.x, while even basic compression stuff wasn't fully useful until .NET 3.x).

    I'm not sure how many of the MSDN System.Linq examples will work, but there can be some useful things for manipulation and lookup in dictionaries once you wrap your head around the other stuff.
     
  9. Raelin_

    Raelin_

    Joined:
    Jul 16, 2014
    Posts:
    20
    I already had the System.Collections.Generic and the System.Linq in, it was showing up red because i put the words in the start function rather that below the public class. thanks for the tip though.