linguistics-evolution-simulator 0.1.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- linguistics_evolution_simulator-0.1.0/PKG-INFO +26 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator/__init__.py +0 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator/data/civilisation.json +74 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator/data/civilisation_init.json +12 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator/data/events.json +75 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator/data/intro.txt +6 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator/data/outro.txt +2 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator/data/words.json +41 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator/main.py +281 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator.egg-info/PKG-INFO +26 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator.egg-info/SOURCES.txt +15 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator.egg-info/dependency_links.txt +1 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator.egg-info/entry_points.txt +2 -0
- linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator.egg-info/top_level.txt +1 -0
- linguistics_evolution_simulator-0.1.0/pyproject.toml +16 -0
- linguistics_evolution_simulator-0.1.0/readme.md +19 -0
- linguistics_evolution_simulator-0.1.0/setup.cfg +4 -0
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: linguistics-evolution-simulator
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: A small civilisation and language evolution simulator.
|
|
5
|
+
Requires-Python: >=3.10
|
|
6
|
+
Description-Content-Type: text/markdown
|
|
7
|
+
|
|
8
|
+
## Features
|
|
9
|
+
This is an attempt at representing linguistic evolution in a human civilisation! It evolves 20 words through 100-year iterations.
|
|
10
|
+
|
|
11
|
+
The game loop is in main; at the beginning, a "civilisation" is generated with random parameters so as to give it unique words for resources; this might also become a game mechanic in the future. Afterwards, a quantity of words "evolve" depending on the modifiers that randomly selected events produce.
|
|
12
|
+
|
|
13
|
+
With regards to the string of "plague" messages, this is to ensure that the population doesn't spiral out of control and lead to many word mutations all at once.
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
## AI use declaration
|
|
17
|
+
As I said in the project description, virtually none of the code had AI input; as far as I can remember, all the code was written myself, with AI only acting occasionally as a tool that I use for better-quality brainstorming and planning.
|
|
18
|
+
|
|
19
|
+
However, there was one major task that I had to rely on AI for guidance, which is the publishing to PyPI step in preparation for shipping. I am personally very inexperienced with the whole project lifecycle, and especially shipping, so I had to rely on it to guide me through this process of packing everything in and replacing some file paths in the source code. In any case, this is good project experience and something that I learned!
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
## Installation
|
|
23
|
+
Install with pipx:
|
|
24
|
+
|
|
25
|
+
```bash
|
|
26
|
+
pipx install linguistics-evolution-simulator
|
|
File without changes
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
{
|
|
2
|
+
"geographies": [
|
|
3
|
+
"Forest",
|
|
4
|
+
"Plains",
|
|
5
|
+
"Desert/Steppe",
|
|
6
|
+
"Mountains/Valley",
|
|
7
|
+
"Wetlands (Ocean, River)"
|
|
8
|
+
],
|
|
9
|
+
|
|
10
|
+
"resources": {
|
|
11
|
+
"specific": {
|
|
12
|
+
"Forest": [
|
|
13
|
+
"Timber",
|
|
14
|
+
"Furs",
|
|
15
|
+
"Honey"
|
|
16
|
+
],
|
|
17
|
+
|
|
18
|
+
"Plains": [
|
|
19
|
+
"Wheat",
|
|
20
|
+
"Barley",
|
|
21
|
+
"Oats",
|
|
22
|
+
"Horses",
|
|
23
|
+
"Cattle"
|
|
24
|
+
],
|
|
25
|
+
|
|
26
|
+
"Desert/Steppe": [
|
|
27
|
+
"Dates",
|
|
28
|
+
"Ivory",
|
|
29
|
+
"Camels"
|
|
30
|
+
],
|
|
31
|
+
|
|
32
|
+
"Mountains/Valley": [
|
|
33
|
+
"Stone",
|
|
34
|
+
"Marble",
|
|
35
|
+
"Limestone",
|
|
36
|
+
"Goats"
|
|
37
|
+
],
|
|
38
|
+
|
|
39
|
+
"Wetlands (Ocean, River)": [
|
|
40
|
+
"Fish",
|
|
41
|
+
"Rice",
|
|
42
|
+
"Papyrus",
|
|
43
|
+
"Clay"
|
|
44
|
+
]
|
|
45
|
+
},
|
|
46
|
+
|
|
47
|
+
"general": [
|
|
48
|
+
"Olives",
|
|
49
|
+
"Grapes",
|
|
50
|
+
"Salt",
|
|
51
|
+
"Iron",
|
|
52
|
+
"Copper",
|
|
53
|
+
"Tin",
|
|
54
|
+
"Lead",
|
|
55
|
+
"Silver",
|
|
56
|
+
"Gold",
|
|
57
|
+
"Coal",
|
|
58
|
+
"Charcoal",
|
|
59
|
+
"Wool",
|
|
60
|
+
"Leather",
|
|
61
|
+
"Sheep",
|
|
62
|
+
"Pigs",
|
|
63
|
+
"Spices",
|
|
64
|
+
"Herbs",
|
|
65
|
+
"Dyes",
|
|
66
|
+
"Silk",
|
|
67
|
+
"Cotton"
|
|
68
|
+
]
|
|
69
|
+
},
|
|
70
|
+
|
|
71
|
+
"quirks": {
|
|
72
|
+
"empty": "so far"
|
|
73
|
+
}
|
|
74
|
+
}
|
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
{
|
|
2
|
+
"events": [
|
|
3
|
+
{
|
|
4
|
+
"event": "Conquest - the conquerors have introduced new words.",
|
|
5
|
+
"word_shift_modifier": 3,
|
|
6
|
+
"word_addition_modifier": 0,
|
|
7
|
+
"grammar_shift_modifier": 0,
|
|
8
|
+
"population_shift_modifier": -0.02
|
|
9
|
+
},
|
|
10
|
+
|
|
11
|
+
{
|
|
12
|
+
"event": "Slang - the youngsters, adding new vocabulary!",
|
|
13
|
+
"word_shift_modifier": 4,
|
|
14
|
+
"word_addition_modifier": 0,
|
|
15
|
+
"grammar_shift_modifier": 0,
|
|
16
|
+
"population_shift_modifier": 0
|
|
17
|
+
},
|
|
18
|
+
|
|
19
|
+
{
|
|
20
|
+
"event": "Trade - traders from all across the region bring their words.",
|
|
21
|
+
"word_shift_modifier": 1,
|
|
22
|
+
"word_addition_modifier": 0,
|
|
23
|
+
"grammar_shift_modifier": 0,
|
|
24
|
+
"population_shift_modifier": 0.01
|
|
25
|
+
},
|
|
26
|
+
|
|
27
|
+
{
|
|
28
|
+
"event": "Migration - other tribes and peoples have brought their tongues with them.",
|
|
29
|
+
"word_shift_modifier": 2,
|
|
30
|
+
"word_addition_modifier": 0,
|
|
31
|
+
"grammar_shift_modifier": 0,
|
|
32
|
+
"population_shift_modifier": 0.1
|
|
33
|
+
},
|
|
34
|
+
|
|
35
|
+
{
|
|
36
|
+
"event": "Isolation - less people to talk with, less words get made up.",
|
|
37
|
+
"word_shift_modifier": -1,
|
|
38
|
+
"word_addition_modifier": 0,
|
|
39
|
+
"grammar_shift_modifier": 0,
|
|
40
|
+
"population_shift_modifier": 0
|
|
41
|
+
},
|
|
42
|
+
|
|
43
|
+
{
|
|
44
|
+
"event": "Writing - words being written down offer a spelling that is less modifiable.",
|
|
45
|
+
"word_shift_modifier": -1,
|
|
46
|
+
"word_addition_modifier": 0,
|
|
47
|
+
"grammar_shift_modifier": 0,
|
|
48
|
+
"population_shift_modifier": 0
|
|
49
|
+
},
|
|
50
|
+
|
|
51
|
+
{
|
|
52
|
+
"event": "Political Unification - the new regime is making efforts to unify the language.",
|
|
53
|
+
"word_shift_modifier": -2,
|
|
54
|
+
"word_addition_modifier": 0,
|
|
55
|
+
"grammar_shift_modifier": 0,
|
|
56
|
+
"population_shift_modifier": 0
|
|
57
|
+
},
|
|
58
|
+
|
|
59
|
+
{
|
|
60
|
+
"event": "Education - More people know how to read and write standard words, and they don't change as much.",
|
|
61
|
+
"word_shift_modifier": -4,
|
|
62
|
+
"word_addition_modifier": 0,
|
|
63
|
+
"grammar_shift_modifier": 0,
|
|
64
|
+
"population_shift_modifier": 0
|
|
65
|
+
},
|
|
66
|
+
|
|
67
|
+
{
|
|
68
|
+
"event": "Plague - People are dying in droves, and many words are dying off.",
|
|
69
|
+
"word_shift_modifier": -3,
|
|
70
|
+
"word_addition_modifier": 0,
|
|
71
|
+
"grammar_shift_modifier": 0,
|
|
72
|
+
"population_shift_modifier": -0.2
|
|
73
|
+
}
|
|
74
|
+
]
|
|
75
|
+
}
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
Welcome to the Linguistics Simulator!
|
|
2
|
+
This is a little mockup of how linguistics evolution can occur within human populations.
|
|
3
|
+
But a disclaimer first.
|
|
4
|
+
I am not a linguistics professor, so there probably are issues in terms of evolutionary accuracy.
|
|
5
|
+
I am open to any feedback if that's the case.
|
|
6
|
+
But sit back, relax, and see a little civilisation evolve!
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
{
|
|
2
|
+
"general": [
|
|
3
|
+
"water",
|
|
4
|
+
"food",
|
|
5
|
+
"house",
|
|
6
|
+
"way",
|
|
7
|
+
"person",
|
|
8
|
+
"sleep",
|
|
9
|
+
"hand",
|
|
10
|
+
"world",
|
|
11
|
+
"life",
|
|
12
|
+
"day",
|
|
13
|
+
"time"
|
|
14
|
+
],
|
|
15
|
+
|
|
16
|
+
"antiquity": [
|
|
17
|
+
"slave",
|
|
18
|
+
"forum",
|
|
19
|
+
"gods",
|
|
20
|
+
"chief",
|
|
21
|
+
"tribe"
|
|
22
|
+
],
|
|
23
|
+
|
|
24
|
+
"medieval": [
|
|
25
|
+
"merchant",
|
|
26
|
+
"castle",
|
|
27
|
+
"king",
|
|
28
|
+
"village",
|
|
29
|
+
"knight"
|
|
30
|
+
],
|
|
31
|
+
|
|
32
|
+
"modern": [
|
|
33
|
+
"factory",
|
|
34
|
+
"machine",
|
|
35
|
+
"country",
|
|
36
|
+
"city",
|
|
37
|
+
"clock"
|
|
38
|
+
]
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
}
|
|
@@ -0,0 +1,281 @@
|
|
|
1
|
+
import random
|
|
2
|
+
import json
|
|
3
|
+
import time
|
|
4
|
+
|
|
5
|
+
from pathlib import Path
|
|
6
|
+
DATA_DIR = Path(__file__).parent / "data"
|
|
7
|
+
|
|
8
|
+
word_shift_modifier = 0 # number of words that are shifted per iteration
|
|
9
|
+
vowels = str()
|
|
10
|
+
consonants = str()
|
|
11
|
+
modified_words = list()
|
|
12
|
+
|
|
13
|
+
#loading some needed files
|
|
14
|
+
with open(DATA_DIR / "civilisation.json") as file:
|
|
15
|
+
data = json.load(file) #loading all potential environment data
|
|
16
|
+
with open(DATA_DIR / "words.json") as file:
|
|
17
|
+
word_pool = json.load(file)
|
|
18
|
+
with open(DATA_DIR / "events.json") as file:
|
|
19
|
+
all_events = json.load(file)
|
|
20
|
+
|
|
21
|
+
with open(DATA_DIR / "intro.txt", "r") as file:
|
|
22
|
+
intro_lines = file.readlines()
|
|
23
|
+
with open(DATA_DIR / "outro.txt", "r") as file:
|
|
24
|
+
outro_lines = file.readlines()
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
|
|
28
|
+
class Civilisation():
|
|
29
|
+
def __init__(self):
|
|
30
|
+
self.population = random.randint(100, 1000) # Sets beginning population of the civilisation
|
|
31
|
+
self.geography, self.mobility_level = set_geography() # Sets geographical features of the generated civilisation
|
|
32
|
+
self.resources = get_resources(self.geography) # Gets civilisation resources
|
|
33
|
+
self.words = generate_words(self.resources) # Generates word-like words + hardwired to initialise 20 words
|
|
34
|
+
|
|
35
|
+
self.events = None # variable for events - list of event dicts
|
|
36
|
+
|
|
37
|
+
self.write_to_json()
|
|
38
|
+
|
|
39
|
+
def write_to_json(self):
|
|
40
|
+
civilisation_data = {
|
|
41
|
+
"population": self.population,
|
|
42
|
+
"geography": self.geography,
|
|
43
|
+
"mobility_level": self.mobility_level,
|
|
44
|
+
"resources": self.resources,
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
with open(DATA_DIR / "civilisation_init.json", "w") as file:
|
|
48
|
+
json.dump(civilisation_data, file, indent=4)
|
|
49
|
+
|
|
50
|
+
def display_init(self):
|
|
51
|
+
print("\n--- CIVILISATION ---")
|
|
52
|
+
print(f"Population: {self.population}")
|
|
53
|
+
print(f"Geography: {self.geography}")
|
|
54
|
+
print(f"Mobility: {self.mobility_level}/10")
|
|
55
|
+
print(f"Resources: {', '.join(self.resources)}")
|
|
56
|
+
|
|
57
|
+
def display(self, year):
|
|
58
|
+
print("\n--- DASHBOARD ---")
|
|
59
|
+
print(f"Population: {self.population}")
|
|
60
|
+
|
|
61
|
+
if year < 1000:
|
|
62
|
+
era = "Antiquity"
|
|
63
|
+
elif 1000 < year < 2000:
|
|
64
|
+
era = "Medieval"
|
|
65
|
+
else:
|
|
66
|
+
era = "Modern"
|
|
67
|
+
print(f"Era: {era}")
|
|
68
|
+
|
|
69
|
+
print("\nWORDS")
|
|
70
|
+
for i, word in enumerate(self.words):
|
|
71
|
+
if i == 0:
|
|
72
|
+
print("--> General words")
|
|
73
|
+
elif i == 11:
|
|
74
|
+
print("\n--> Resource Words")
|
|
75
|
+
elif i == 16:
|
|
76
|
+
print("\n--> Era-Specific words")
|
|
77
|
+
print(f"{word}: {self.words[word]}")
|
|
78
|
+
|
|
79
|
+
print("\nCHANGES")
|
|
80
|
+
print(f"{word_shift_modifier} words were modified in this iteration.")
|
|
81
|
+
for i, word in enumerate(modified_words):
|
|
82
|
+
print(f"{i + 1}. {word["original"]} --> {word["changed"]}")
|
|
83
|
+
|
|
84
|
+
for i, event in enumerate(self.events):
|
|
85
|
+
print(f"\n{i + 1}.", event["event"])
|
|
86
|
+
print(f"Population change: {round(event["population_shift_modifier"] * 100)}%")
|
|
87
|
+
|
|
88
|
+
def iterate_event(self):
|
|
89
|
+
a = 0
|
|
90
|
+
self.events = []
|
|
91
|
+
|
|
92
|
+
for event in all_events["events"]:
|
|
93
|
+
if self.population > 3000:
|
|
94
|
+
self.events.append(all_events["events"][8])
|
|
95
|
+
continue
|
|
96
|
+
a = random.randint(0, 1)
|
|
97
|
+
if a == 1 and len(self.events) < 3:
|
|
98
|
+
self.events.append(event)
|
|
99
|
+
|
|
100
|
+
def iterate_population(self):
|
|
101
|
+
self.population += round(0.2 * self.population)
|
|
102
|
+
for event in self.events:
|
|
103
|
+
self.population += round(event["population_shift_modifier"] * self.population)
|
|
104
|
+
|
|
105
|
+
def iterate_words(self, year):
|
|
106
|
+
global word_shift_modifier
|
|
107
|
+
word_shift_modifier = 0
|
|
108
|
+
|
|
109
|
+
for event in self.events:
|
|
110
|
+
word_shift_modifier += event["word_shift_modifier"]
|
|
111
|
+
|
|
112
|
+
word_shift_modifier = max(0, min(word_shift_modifier, 10)) # Maximum 10 words changed per iteration
|
|
113
|
+
|
|
114
|
+
|
|
115
|
+
new_era_words = None
|
|
116
|
+
|
|
117
|
+
if year == 1000 or year == 2000:
|
|
118
|
+
if year == 1000:
|
|
119
|
+
new_era_words = word_pool["medieval"]
|
|
120
|
+
else:
|
|
121
|
+
new_era_words = word_pool["modern"]
|
|
122
|
+
|
|
123
|
+
old_words = list(self.words.keys())[-5:]
|
|
124
|
+
|
|
125
|
+
for word in old_words:
|
|
126
|
+
self.words.pop(word)
|
|
127
|
+
|
|
128
|
+
for word in new_era_words[:5]:
|
|
129
|
+
global vowels
|
|
130
|
+
global consonants
|
|
131
|
+
self.words[word] = make_word(vowels, consonants)
|
|
132
|
+
|
|
133
|
+
self.events.append({
|
|
134
|
+
"event": "New era, new words - Change of era! Last 5 era-specific words have changed.",
|
|
135
|
+
"population_shift_modifier": 0,
|
|
136
|
+
"word_shift_modifier": 0
|
|
137
|
+
})
|
|
138
|
+
|
|
139
|
+
|
|
140
|
+
count = 0
|
|
141
|
+
global modified_words
|
|
142
|
+
modified_words = []
|
|
143
|
+
|
|
144
|
+
words_to_change = random.sample(
|
|
145
|
+
list(self.words.keys()),
|
|
146
|
+
min(word_shift_modifier, len(self.words))
|
|
147
|
+
)
|
|
148
|
+
|
|
149
|
+
for word in words_to_change:
|
|
150
|
+
change = {
|
|
151
|
+
"original": self.words[word],
|
|
152
|
+
"changed": None
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
self.words[word] = mutate_word(self.words[word])
|
|
156
|
+
|
|
157
|
+
change["changed"] = self.words[word]
|
|
158
|
+
modified_words.append(change)
|
|
159
|
+
|
|
160
|
+
count += 1
|
|
161
|
+
|
|
162
|
+
|
|
163
|
+
|
|
164
|
+
#----------------------------------------------------------------------------------------
|
|
165
|
+
|
|
166
|
+
|
|
167
|
+
|
|
168
|
+
def set_geography():
|
|
169
|
+
geography = random.choice(data["geographies"])
|
|
170
|
+
|
|
171
|
+
if geography == "Forest":
|
|
172
|
+
mobility_level = random.randint(3, 6)
|
|
173
|
+
elif geography == "Plains":
|
|
174
|
+
mobility_level = random.randint(6, 9)
|
|
175
|
+
elif geography == "Desert/Steppe":
|
|
176
|
+
mobility_level = random.randint(7, 10)
|
|
177
|
+
elif geography == "Mountains/Valley":
|
|
178
|
+
mobility_level = random.randint(0, 3)
|
|
179
|
+
elif geography == "Wetlands (Ocean, River)":
|
|
180
|
+
mobility_level = random.randint(4, 7)
|
|
181
|
+
return geography, mobility_level
|
|
182
|
+
|
|
183
|
+
def get_resources(geography):
|
|
184
|
+
resource_count = 5
|
|
185
|
+
|
|
186
|
+
specific_resources = data["resources"]["specific"][geography]
|
|
187
|
+
general_resources = data["resources"]["general"]
|
|
188
|
+
|
|
189
|
+
resources = random.sample(specific_resources, 2)
|
|
190
|
+
|
|
191
|
+
remaining = resource_count - 2
|
|
192
|
+
|
|
193
|
+
resources += random.sample(general_resources, remaining)
|
|
194
|
+
|
|
195
|
+
return resources
|
|
196
|
+
|
|
197
|
+
def generate_words(resources):
|
|
198
|
+
words = dict()
|
|
199
|
+
for word in word_pool["general"]:
|
|
200
|
+
words[word] = None
|
|
201
|
+
for resource in resources:
|
|
202
|
+
words[resource] = None
|
|
203
|
+
for word in word_pool["antiquity"]:
|
|
204
|
+
words[word] = None
|
|
205
|
+
|
|
206
|
+
all_vowels = "aeiou"
|
|
207
|
+
all_consonants = "bcdfghjklmnpqrstvwxyz"
|
|
208
|
+
|
|
209
|
+
global vowels
|
|
210
|
+
global consonants
|
|
211
|
+
vowels = random.sample(all_vowels, 3)
|
|
212
|
+
consonants = random.sample(all_consonants, 10)
|
|
213
|
+
|
|
214
|
+
for word in words:
|
|
215
|
+
words[word] = make_word(vowels, consonants)
|
|
216
|
+
|
|
217
|
+
return words
|
|
218
|
+
|
|
219
|
+
def make_word(vowels, consonants):
|
|
220
|
+
word = ""
|
|
221
|
+
for _ in range(random.randint(2, 3)):
|
|
222
|
+
word += random.choice(consonants)
|
|
223
|
+
word += random.choice(vowels)
|
|
224
|
+
|
|
225
|
+
return word
|
|
226
|
+
|
|
227
|
+
def mutate_word(word):
|
|
228
|
+
vowels = "aeiou"
|
|
229
|
+
consonants = "bcdfghjklmnpqrstvwxyz"
|
|
230
|
+
|
|
231
|
+
index = random.randint(0, len(word) - 1)
|
|
232
|
+
old_letter = word[index]
|
|
233
|
+
|
|
234
|
+
if old_letter in vowels:
|
|
235
|
+
possible_letters = vowels
|
|
236
|
+
else:
|
|
237
|
+
possible_letters = consonants
|
|
238
|
+
|
|
239
|
+
new_letter = random.choice(possible_letters)
|
|
240
|
+
|
|
241
|
+
while new_letter == old_letter:
|
|
242
|
+
new_letter = random.choice(possible_letters)
|
|
243
|
+
|
|
244
|
+
return word[:index] + new_letter + word[index + 1:]
|
|
245
|
+
|
|
246
|
+
|
|
247
|
+
|
|
248
|
+
def main():
|
|
249
|
+
civilisation = Civilisation()
|
|
250
|
+
running = True
|
|
251
|
+
year = 0
|
|
252
|
+
|
|
253
|
+
while running:
|
|
254
|
+
if year == 0:
|
|
255
|
+
for line in intro_lines:
|
|
256
|
+
print(line, end="")
|
|
257
|
+
time.sleep(3)
|
|
258
|
+
print("\n")
|
|
259
|
+
print(f"\nYEAR {year}")
|
|
260
|
+
civilisation.display_init()
|
|
261
|
+
time.sleep(5)
|
|
262
|
+
year += 100
|
|
263
|
+
|
|
264
|
+
print(f"\nYEAR {year}")
|
|
265
|
+
civilisation.iterate_event() # Randomly gets events that are happening this iteration cycle
|
|
266
|
+
civilisation.iterate_population() # Changes civilisation population (mechanic related to some events)
|
|
267
|
+
civilisation.iterate_words(year) # Changes the words in the dashboard
|
|
268
|
+
civilisation.display(year) # Displays a dashboard
|
|
269
|
+
time.sleep(10) # 10 seconds for you to review the word changes in the dashboard
|
|
270
|
+
|
|
271
|
+
if year == 3000:
|
|
272
|
+
print("\n")
|
|
273
|
+
for line in outro_lines:
|
|
274
|
+
print(line, end="")
|
|
275
|
+
time.sleep(3)
|
|
276
|
+
break
|
|
277
|
+
|
|
278
|
+
year += 100
|
|
279
|
+
|
|
280
|
+
if __name__ == "__main__":
|
|
281
|
+
main()
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: linguistics-evolution-simulator
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: A small civilisation and language evolution simulator.
|
|
5
|
+
Requires-Python: >=3.10
|
|
6
|
+
Description-Content-Type: text/markdown
|
|
7
|
+
|
|
8
|
+
## Features
|
|
9
|
+
This is an attempt at representing linguistic evolution in a human civilisation! It evolves 20 words through 100-year iterations.
|
|
10
|
+
|
|
11
|
+
The game loop is in main; at the beginning, a "civilisation" is generated with random parameters so as to give it unique words for resources; this might also become a game mechanic in the future. Afterwards, a quantity of words "evolve" depending on the modifiers that randomly selected events produce.
|
|
12
|
+
|
|
13
|
+
With regards to the string of "plague" messages, this is to ensure that the population doesn't spiral out of control and lead to many word mutations all at once.
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
## AI use declaration
|
|
17
|
+
As I said in the project description, virtually none of the code had AI input; as far as I can remember, all the code was written myself, with AI only acting occasionally as a tool that I use for better-quality brainstorming and planning.
|
|
18
|
+
|
|
19
|
+
However, there was one major task that I had to rely on AI for guidance, which is the publishing to PyPI step in preparation for shipping. I am personally very inexperienced with the whole project lifecycle, and especially shipping, so I had to rely on it to guide me through this process of packing everything in and replacing some file paths in the source code. In any case, this is good project experience and something that I learned!
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
## Installation
|
|
23
|
+
Install with pipx:
|
|
24
|
+
|
|
25
|
+
```bash
|
|
26
|
+
pipx install linguistics-evolution-simulator
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
pyproject.toml
|
|
2
|
+
readme.md
|
|
3
|
+
linguistics_evolution_simulator/__init__.py
|
|
4
|
+
linguistics_evolution_simulator/main.py
|
|
5
|
+
linguistics_evolution_simulator.egg-info/PKG-INFO
|
|
6
|
+
linguistics_evolution_simulator.egg-info/SOURCES.txt
|
|
7
|
+
linguistics_evolution_simulator.egg-info/dependency_links.txt
|
|
8
|
+
linguistics_evolution_simulator.egg-info/entry_points.txt
|
|
9
|
+
linguistics_evolution_simulator.egg-info/top_level.txt
|
|
10
|
+
linguistics_evolution_simulator/data/civilisation.json
|
|
11
|
+
linguistics_evolution_simulator/data/civilisation_init.json
|
|
12
|
+
linguistics_evolution_simulator/data/events.json
|
|
13
|
+
linguistics_evolution_simulator/data/intro.txt
|
|
14
|
+
linguistics_evolution_simulator/data/outro.txt
|
|
15
|
+
linguistics_evolution_simulator/data/words.json
|
linguistics_evolution_simulator-0.1.0/linguistics_evolution_simulator.egg-info/dependency_links.txt
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
linguistics_evolution_simulator
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
[build-system]
|
|
2
|
+
requires = ["setuptools>=68"]
|
|
3
|
+
build-backend = "setuptools.build_meta"
|
|
4
|
+
|
|
5
|
+
[project]
|
|
6
|
+
name = "linguistics-evolution-simulator"
|
|
7
|
+
version = "0.1.0"
|
|
8
|
+
description = "A small civilisation and language evolution simulator."
|
|
9
|
+
readme = "readme.md"
|
|
10
|
+
requires-python = ">=3.10"
|
|
11
|
+
|
|
12
|
+
[project.scripts]
|
|
13
|
+
linguistics-sim = "linguistics_evolution_simulator.main:main"
|
|
14
|
+
|
|
15
|
+
[tool.setuptools.package-data]
|
|
16
|
+
linguistics_evolution_simulator = ["data/*.json", "data/*.txt"]
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
## Features
|
|
2
|
+
This is an attempt at representing linguistic evolution in a human civilisation! It evolves 20 words through 100-year iterations.
|
|
3
|
+
|
|
4
|
+
The game loop is in main; at the beginning, a "civilisation" is generated with random parameters so as to give it unique words for resources; this might also become a game mechanic in the future. Afterwards, a quantity of words "evolve" depending on the modifiers that randomly selected events produce.
|
|
5
|
+
|
|
6
|
+
With regards to the string of "plague" messages, this is to ensure that the population doesn't spiral out of control and lead to many word mutations all at once.
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
## AI use declaration
|
|
10
|
+
As I said in the project description, virtually none of the code had AI input; as far as I can remember, all the code was written myself, with AI only acting occasionally as a tool that I use for better-quality brainstorming and planning.
|
|
11
|
+
|
|
12
|
+
However, there was one major task that I had to rely on AI for guidance, which is the publishing to PyPI step in preparation for shipping. I am personally very inexperienced with the whole project lifecycle, and especially shipping, so I had to rely on it to guide me through this process of packing everything in and replacing some file paths in the source code. In any case, this is good project experience and something that I learned!
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
## Installation
|
|
16
|
+
Install with pipx:
|
|
17
|
+
|
|
18
|
+
```bash
|
|
19
|
+
pipx install linguistics-evolution-simulator
|