dynamic-learning-model 2.1__tar.gz → 3.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.
- {dynamic_learning_model-2.1/dynamic_learning_model.egg-info → dynamic_learning_model-3.0}/PKG-INFO +8 -12
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/README.md +6 -11
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/dlm/DLM.py +103 -81
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0/dynamic_learning_model.egg-info}/PKG-INFO +8 -12
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/dynamic_learning_model.egg-info/requires.txt +1 -0
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/setup.py +3 -2
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/LICENSE +0 -0
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/dlm/__init__.py +0 -0
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/dynamic_learning_model.egg-info/SOURCES.txt +0 -0
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/dynamic_learning_model.egg-info/dependency_links.txt +0 -0
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/dynamic_learning_model.egg-info/top_level.txt +0 -0
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/pyproject.toml +0 -0
- {dynamic_learning_model-2.1 → dynamic_learning_model-3.0}/setup.cfg +0 -0
{dynamic_learning_model-2.1/dynamic_learning_model.egg-info → dynamic_learning_model-3.0}/PKG-INFO
RENAMED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: dynamic-learning-model
|
|
3
|
-
Version:
|
|
3
|
+
Version: 3.0
|
|
4
4
|
Summary: A Dynamic Learning Model for processing NLP queries using hybrid AI and reasoning.
|
|
5
5
|
Home-page: https://github.com/VigneshT24/Dynamic_Learning_Model
|
|
6
6
|
Author: Vignesh Thondikulam
|
|
@@ -16,6 +16,7 @@ Requires-Dist: nltk
|
|
|
16
16
|
Requires-Dist: spacy
|
|
17
17
|
Requires-Dist: better_profanity
|
|
18
18
|
Requires-Dist: word2number
|
|
19
|
+
Requires-Dist: transformers
|
|
19
20
|
Dynamic: author
|
|
20
21
|
Dynamic: author-email
|
|
21
22
|
Dynamic: classifier
|
|
@@ -30,6 +31,7 @@ Dynamic: summary
|
|
|
30
31
|
|
|
31
32
|

|
|
32
33
|

|
|
34
|
+

|
|
33
35
|
|
|
34
36
|
# Dynamic Learning Model
|
|
35
37
|
**ABOUT**:
|
|
@@ -50,8 +52,7 @@ Whether you're building a student support bot, a domain-specific assistant, or a
|
|
|
50
52
|
* The constructor requires passing in two parameters:
|
|
51
53
|
- Bot Mode:
|
|
52
54
|
- 'learn' = Enables training using the memory model. The bot can be updated with new information,
|
|
53
|
-
- '
|
|
54
|
-
- 'compute' = Activates the computation model for processing and solving queries algorithmically (no training)
|
|
55
|
+
- 'apply' = The bot automatically switches between its "compute" and "memory" model depending on the query asked
|
|
55
56
|
- Empty SQL Database for training the bot with queries and for the memory model
|
|
56
57
|
* The ask() method also requires passing in two parameters:
|
|
57
58
|
- Query: "What is the definition of FAFSA" (as an example)
|
|
@@ -74,22 +75,17 @@ training_bot = DLM("learn", "college_knowledge.db")
|
|
|
74
75
|
training_bot.ask("What is FAFSA in college?", True)
|
|
75
76
|
```
|
|
76
77
|
|
|
77
|
-
('
|
|
78
|
+
('apply' mode [deployment/production use after training])
|
|
78
79
|
```python
|
|
79
80
|
from dlm import DLM
|
|
80
81
|
|
|
81
|
-
commercial_bot = DLM("
|
|
82
|
+
commercial_bot = DLM("apply", "college_knowledge.db")
|
|
82
83
|
|
|
83
84
|
commercial_bot.ask("What is the difference between FAFSA and CADAA in California?", False)
|
|
84
|
-
```
|
|
85
|
-
|
|
86
|
-
('compute' mode [computation queries])
|
|
87
|
-
```python
|
|
88
|
-
from dlm import DLM
|
|
89
85
|
|
|
90
|
-
|
|
86
|
+
# or
|
|
91
87
|
|
|
92
|
-
|
|
88
|
+
commercial_bot.ask("Tell me the result for the following: 5 * 5 * 5 + 5 / 5", True)
|
|
93
89
|
```
|
|
94
90
|
|
|
95
91
|
**HIGH-LEVEL PIPELINE VISUAL**:
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|

|
|
2
2
|

|
|
3
|
+

|
|
3
4
|
|
|
4
5
|
# Dynamic Learning Model
|
|
5
6
|
**ABOUT**:
|
|
@@ -20,8 +21,7 @@ Whether you're building a student support bot, a domain-specific assistant, or a
|
|
|
20
21
|
* The constructor requires passing in two parameters:
|
|
21
22
|
- Bot Mode:
|
|
22
23
|
- 'learn' = Enables training using the memory model. The bot can be updated with new information,
|
|
23
|
-
- '
|
|
24
|
-
- 'compute' = Activates the computation model for processing and solving queries algorithmically (no training)
|
|
24
|
+
- 'apply' = The bot automatically switches between its "compute" and "memory" model depending on the query asked
|
|
25
25
|
- Empty SQL Database for training the bot with queries and for the memory model
|
|
26
26
|
* The ask() method also requires passing in two parameters:
|
|
27
27
|
- Query: "What is the definition of FAFSA" (as an example)
|
|
@@ -44,22 +44,17 @@ training_bot = DLM("learn", "college_knowledge.db")
|
|
|
44
44
|
training_bot.ask("What is FAFSA in college?", True)
|
|
45
45
|
```
|
|
46
46
|
|
|
47
|
-
('
|
|
47
|
+
('apply' mode [deployment/production use after training])
|
|
48
48
|
```python
|
|
49
49
|
from dlm import DLM
|
|
50
50
|
|
|
51
|
-
commercial_bot = DLM("
|
|
51
|
+
commercial_bot = DLM("apply", "college_knowledge.db")
|
|
52
52
|
|
|
53
53
|
commercial_bot.ask("What is the difference between FAFSA and CADAA in California?", False)
|
|
54
|
-
```
|
|
55
|
-
|
|
56
|
-
('compute' mode [computation queries])
|
|
57
|
-
```python
|
|
58
|
-
from dlm import DLM
|
|
59
54
|
|
|
60
|
-
|
|
55
|
+
# or
|
|
61
56
|
|
|
62
|
-
|
|
57
|
+
commercial_bot.ask("Tell me the result for the following: 5 * 5 * 5 + 5 / 5", True)
|
|
63
58
|
```
|
|
64
59
|
|
|
65
60
|
**HIGH-LEVEL PIPELINE VISUAL**:
|
|
@@ -7,6 +7,7 @@ import sqlite3
|
|
|
7
7
|
import re
|
|
8
8
|
import nltk
|
|
9
9
|
import math
|
|
10
|
+
from transformers import pipeline
|
|
10
11
|
from better_profanity import profanity
|
|
11
12
|
from nltk.corpus import names
|
|
12
13
|
from word2number import w2n
|
|
@@ -19,12 +20,14 @@ class DLM:
|
|
|
19
20
|
__nlp = None # Spacy NLP analysis
|
|
20
21
|
__tone = None # sentimental tone of user query
|
|
21
22
|
__trainingPwd = "371507" # password to enter training mode
|
|
22
|
-
__mode = None # either "learn"
|
|
23
|
+
__mode = None # either "learn" or "apply"
|
|
23
24
|
__unsure_while_thinking = False # if uncertain while thinking, then it will let the user know that
|
|
24
25
|
__nlp_similarity_value = None # saves the similarity value by doing SpaCy calculation (for debugging)
|
|
25
26
|
__special_stripped_query = None # saves query without any special words for reduced interference while vector calculating
|
|
26
27
|
__nltk_names = set(name.lower() for name in names.words()) # list of name corpus to be identified in complex word problems
|
|
27
28
|
__refuse_to_respond = False # if profanity or all caps-lock frustration is detected, refuse to respond and suggest user to try again (bot respect)
|
|
29
|
+
__model = None # BETA: bot automatically chooses between "compute" or "memory" model based on query type
|
|
30
|
+
__hf_classifier = None # loading huggingface model to determine the query type for auto_mode
|
|
28
31
|
|
|
29
32
|
# personalized responses to let the user know that the bot doesn't know the answer
|
|
30
33
|
__fallback_responses = [
|
|
@@ -223,8 +226,8 @@ class DLM:
|
|
|
223
226
|
},
|
|
224
227
|
"rectangle": {
|
|
225
228
|
"keywords": ["area", "rectangle"],
|
|
226
|
-
"params": ["
|
|
227
|
-
"formula": lambda d: d["
|
|
229
|
+
"params": ["height", "width"],
|
|
230
|
+
"formula": lambda d: d["height"] * d["width"]
|
|
228
231
|
},
|
|
229
232
|
"parallelogram": {
|
|
230
233
|
"keywords": ["area", "parallelogram"],
|
|
@@ -265,8 +268,10 @@ class DLM:
|
|
|
265
268
|
},
|
|
266
269
|
"rectangular prism": {
|
|
267
270
|
"keywords": ["volume", "rectangular prism"],
|
|
268
|
-
"params": ["length", "width", "height"],
|
|
269
|
-
"formula": lambda d: d["length"] * d["width"] * d["height"]
|
|
271
|
+
# "params": ["length", "width", "height"],
|
|
272
|
+
# "formula": lambda d: d["length"] * d["width"] * d["height"]
|
|
273
|
+
"params": ["height", "length", "width"],
|
|
274
|
+
"formula": lambda d: d["height"] * d["length"] * d["width"]
|
|
270
275
|
},
|
|
271
276
|
"cylinder": {
|
|
272
277
|
"keywords": ["volume", "cylinder"],
|
|
@@ -354,21 +359,22 @@ class DLM:
|
|
|
354
359
|
|
|
355
360
|
Parameters:
|
|
356
361
|
mode (str): The access mode. Options:
|
|
357
|
-
'learn' for training mode (to train the bot with queries)
|
|
358
|
-
'
|
|
359
|
-
'compute' for mathematical queries (for arithmetic, conversion, or geometric queries).
|
|
362
|
+
'learn' for training mode (to train the bot with queries).
|
|
363
|
+
'apply' for a trained model to choose between compute and memory mode.
|
|
360
364
|
db_filename (str): The SQLite database file used to train and retrieve
|
|
361
365
|
question-answer-category triples.
|
|
362
366
|
|
|
363
367
|
Behavior:
|
|
364
368
|
- Loads the SpaCy NLP model ('en_core_web_lg').
|
|
369
|
+
- Loads the HuggingFace model for auto-model detection.
|
|
365
370
|
- Loads Better-Profanity for profane phrase sensing.
|
|
366
371
|
- Connects to the specified SQLite database file.
|
|
367
|
-
- Set appropriate mode value
|
|
368
|
-
- Verify login information based on mode
|
|
372
|
+
- Set appropriate mode value.
|
|
373
|
+
- Verify login information based on mode.
|
|
369
374
|
- Ensures the required table structure exists (creates if missing).
|
|
370
375
|
"""
|
|
371
376
|
self.__nlp = spacy.load("en_core_web_lg")
|
|
377
|
+
self.__hf_classifier = pipeline("zero-shot-classification", model="facebook/bart-large-mnli")
|
|
372
378
|
profanity.load_censor_words()
|
|
373
379
|
self.__filename = db_filename
|
|
374
380
|
self.__mode = mode
|
|
@@ -377,25 +383,22 @@ class DLM:
|
|
|
377
383
|
|
|
378
384
|
def __login_verification(self, mode): # no return, void
|
|
379
385
|
"""
|
|
380
|
-
Verify and initialize the selected access mode (Learn
|
|
386
|
+
Verify and initialize the selected access mode (Learn or Apply).
|
|
381
387
|
|
|
382
388
|
Parameters:
|
|
383
389
|
mode (str): The access mode. Options:
|
|
384
|
-
'learn' for training mode (to train the bot with queries)
|
|
385
|
-
'
|
|
386
|
-
'compute' for mathematical queries (for arithmetic or conversion queries).
|
|
390
|
+
'learn' for training mode (to train the bot with queries).
|
|
391
|
+
'apply' for trained model to choose "compute" or "memory" mode.
|
|
387
392
|
Behavior:
|
|
388
393
|
- If mode is 'learn', prompts for a password and displays mandatory training instructions.
|
|
389
|
-
- If mode is '
|
|
390
|
-
- If mode is 'compute', proceeds with computation model with reasoning capabilities.
|
|
394
|
+
- If mode is 'apply', enters without prompting password and allows model to answer queries.
|
|
391
395
|
"""
|
|
392
396
|
if mode.lower() == "learn":
|
|
393
397
|
password = input("Enter the password to enter Learn Mode: ")
|
|
394
398
|
while password != self.__trainingPwd:
|
|
395
|
-
password = input(
|
|
396
|
-
"Password is incorrect, try again or type 'stop' to enter in recall mode instead: ")
|
|
399
|
+
password = input("Password is incorrect, try again or type 'stop' to enter in apply mode instead: ")
|
|
397
400
|
if password.lower() == "stop":
|
|
398
|
-
self.__mode = "
|
|
401
|
+
self.__mode = "apply"
|
|
399
402
|
print("\n")
|
|
400
403
|
break
|
|
401
404
|
if password == self.__trainingPwd:
|
|
@@ -416,16 +419,13 @@ class DLM:
|
|
|
416
419
|
confirmation = input(
|
|
417
420
|
"Make sure to understand and note these instructions somewhere as the generated responses would get corrupt otherwise.\nType 'Y' if you understood: ")
|
|
418
421
|
while confirmation.lower() != "y": # trainers must understand the instructions above
|
|
419
|
-
confirmation = input(
|
|
420
|
-
"You cannot proceed to train without understanding the instructions aforementioned. Type 'Y' to continue: ")
|
|
422
|
+
confirmation = input("You cannot proceed to train without understanding the instructions aforementioned. Type 'Y' to continue: ")
|
|
421
423
|
self.__mode = "learn"
|
|
422
424
|
print("\n")
|
|
423
|
-
self.
|
|
425
|
+
self.__loading_animation("Logging in as Trainer", 0.6)
|
|
424
426
|
print("\n")
|
|
425
|
-
elif mode.lower() == "recall":
|
|
426
|
-
self.__mode = "recall"
|
|
427
427
|
else:
|
|
428
|
-
self.__mode = "
|
|
428
|
+
self.__mode = "apply"
|
|
429
429
|
|
|
430
430
|
def __create_table_if_missing(self): # no return, void
|
|
431
431
|
"""
|
|
@@ -434,10 +434,10 @@ class DLM:
|
|
|
434
434
|
Behavior:
|
|
435
435
|
- Establishes a connection to the SQLite database specified by self.__filename.
|
|
436
436
|
- Creates the 'knowledge_base' table if it does not exist, with the following columns:
|
|
437
|
-
- id (INTEGER, PRIMARY KEY, AUTOINCREMENT)
|
|
438
|
-
- question (TEXT, NOT NULL, UNIQUE)
|
|
439
|
-
- answer (TEXT, NOT NULL)
|
|
440
|
-
- category (TEXT, NOT NULL)
|
|
437
|
+
- id (INTEGER, PRIMARY KEY, AUTOINCREMENT).
|
|
438
|
+
- question (TEXT, NOT NULL, UNIQUE).
|
|
439
|
+
- answer (TEXT, NOT NULL).
|
|
440
|
+
- category (TEXT, NOT NULL).
|
|
441
441
|
- If the table already exists but is missing the 'category' column, the method adds it with a default empty string.
|
|
442
442
|
- Used exclusively within the class constructor to ensure the database schema is properly initialized.
|
|
443
443
|
"""
|
|
@@ -526,7 +526,7 @@ class DLM:
|
|
|
526
526
|
|
|
527
527
|
@staticmethod
|
|
528
528
|
# loading animation for bot thought process
|
|
529
|
-
def
|
|
529
|
+
def __loading_animation(user_input, duration): # no return, void
|
|
530
530
|
for seconds in range(0, 3):
|
|
531
531
|
print(f"{'\033[33m'}\r{user_input}{'.' * (seconds + 1)} {'\033[0m'}", end="", flush=True)
|
|
532
532
|
time.sleep(duration)
|
|
@@ -546,7 +546,7 @@ class DLM:
|
|
|
546
546
|
- Tokenizes the input into words.
|
|
547
547
|
- Removes filler words unless:
|
|
548
548
|
- It's the first word and part of the exception list.
|
|
549
|
-
- The current
|
|
549
|
+
- The current model is 'compute' and the word is a computation keyword.
|
|
550
550
|
- Preserves word order while removing duplicates.
|
|
551
551
|
- Joins the remaining words back into a single filtered string.
|
|
552
552
|
"""
|
|
@@ -569,7 +569,7 @@ class DLM:
|
|
|
569
569
|
for kws in self.__computation_identifiers.values()
|
|
570
570
|
for kw in kws)
|
|
571
571
|
|
|
572
|
-
if word_lowered not in self.__filler_words or (self.
|
|
572
|
+
if word_lowered not in self.__filler_words or (self.__model == "compute" and is_computation_kw):
|
|
573
573
|
filtered_words.append(word)
|
|
574
574
|
|
|
575
575
|
# remove duplicates while preserving order (numbers excluded)
|
|
@@ -599,12 +599,12 @@ class DLM:
|
|
|
599
599
|
Behavior:
|
|
600
600
|
- Detects aggressive language using profanity filtering.
|
|
601
601
|
- Analyzes punctuation and casing to infer emotional tone such as:
|
|
602
|
-
- 'angry aggressive' for profane content - refuse to respond
|
|
603
|
-
- 'angry frustrated' for all-uppercase text - refuse to respond
|
|
604
|
-
- 'angry confused' for combined "?" and "!"
|
|
605
|
-
- 'angry excited' for "!" only
|
|
606
|
-
- 'confused unclear' for "?" only
|
|
607
|
-
- 'doubtful uncertain' for ellipses ("..." or "..")
|
|
602
|
+
- 'angry aggressive' for profane content - refuse to respond.
|
|
603
|
+
- 'angry frustrated' for all-uppercase text - refuse to respond.
|
|
604
|
+
- 'angry confused' for combined "?" and "!".
|
|
605
|
+
- 'angry excited' for "!" only.
|
|
606
|
+
- 'confused unclear' for "?" only.
|
|
607
|
+
- 'doubtful uncertain' for ellipses ("..." or "..").
|
|
608
608
|
- Stores the result in self.__tone as a string label.
|
|
609
609
|
"""
|
|
610
610
|
is_profane = profanity.contains_profanity(orig_input)
|
|
@@ -629,20 +629,20 @@ class DLM:
|
|
|
629
629
|
|
|
630
630
|
def __geometric_calculation(self, filtered_query, display_thought): # returns float result or None
|
|
631
631
|
"""
|
|
632
|
-
Perform geometric problems that will be called inside perform_advanced_CoT
|
|
632
|
+
Perform geometric problems that will be called inside perform_advanced_CoT.
|
|
633
633
|
|
|
634
634
|
Parameters:
|
|
635
|
-
filtered_query (str): user query that has been filtered to have mostly computational details
|
|
636
|
-
display_thought (bool): Indicates whether the user wants to have the bot display its thought process or just give the answer
|
|
635
|
+
filtered_query (str): user query that has been filtered to have mostly computational details.
|
|
636
|
+
display_thought (bool): Indicates whether the user wants to have the bot display its thought process or just give the answer.
|
|
637
637
|
|
|
638
638
|
Returns:
|
|
639
|
-
float: The result after computing the geometric calculation
|
|
639
|
+
float: The result after computing the geometric calculation.
|
|
640
640
|
|
|
641
641
|
Behavior:
|
|
642
|
-
- Search through query to find specific keywords like 'area' or 'volume'
|
|
643
|
-
- Then, search to find shape or object to perform math on like 'triangle' or 'square'
|
|
644
|
-
- Find numbers associated with object details and store in appropriate list
|
|
645
|
-
- Finally, find appropriate formula with identifiers and plug in and return answer
|
|
642
|
+
- Search through query to find specific keywords like 'area' or 'volume'.
|
|
643
|
+
- Then, search to find shape or object to perform math on like 'triangle' or 'square'.
|
|
644
|
+
- Find numbers associated with object details and store in appropriate list.
|
|
645
|
+
- Finally, find appropriate formula with identifiers and plug in and return answer.
|
|
646
646
|
|
|
647
647
|
"""
|
|
648
648
|
height_value = None
|
|
@@ -708,9 +708,13 @@ class DLM:
|
|
|
708
708
|
break
|
|
709
709
|
is_similar = difflib.get_close_matches(phrase, [obj], n=1, cutoff=0.70)
|
|
710
710
|
if is_similar and is_similar[0] == obj:
|
|
711
|
-
|
|
712
|
-
|
|
713
|
-
|
|
711
|
+
geom_type = self.__geometric_calculation_identifiers[obj]["keywords"]
|
|
712
|
+
if (lower_tokens.__contains__(geom_type[0])):
|
|
713
|
+
object_intel.extend(geom_type)
|
|
714
|
+
end_check = True
|
|
715
|
+
break
|
|
716
|
+
else:
|
|
717
|
+
continue
|
|
714
718
|
if end_check:
|
|
715
719
|
break
|
|
716
720
|
|
|
@@ -733,19 +737,19 @@ class DLM:
|
|
|
733
737
|
# if allowed, display the inner thought process
|
|
734
738
|
obj_name = object_intel[1]
|
|
735
739
|
if display_thought:
|
|
736
|
-
self.
|
|
740
|
+
self.__loading_animation(f"It seems that the user wants to compute the {' of a '.join(object_intel)}", 0.5)
|
|
737
741
|
if height_value is not None:
|
|
738
|
-
self.
|
|
742
|
+
self.__loading_animation(
|
|
739
743
|
f"* The user has mentioned that the height of the {obj_name} object is {height_value}", 0.4)
|
|
740
744
|
else:
|
|
741
|
-
self.
|
|
745
|
+
self.__loading_animation(
|
|
742
746
|
f"* The {object_intel[1]} object has no height associated with it, so moving on", 0.4)
|
|
743
747
|
if len(other_values) > 0:
|
|
744
|
-
self.
|
|
748
|
+
self.__loading_animation(
|
|
745
749
|
f"* Additional numerical values associated with the dimensions of the {obj_name} object is {' and '.join(str(v) for v in other_values)}",
|
|
746
750
|
0.4)
|
|
747
751
|
else:
|
|
748
|
-
self.
|
|
752
|
+
self.__loading_animation(
|
|
749
753
|
f"* No additional numerical values associated with the dimensions of the {obj_name} were given",
|
|
750
754
|
0.4)
|
|
751
755
|
|
|
@@ -759,9 +763,13 @@ class DLM:
|
|
|
759
763
|
try:
|
|
760
764
|
if "height" in params:
|
|
761
765
|
formula_inputs["height"] = height_value
|
|
766
|
+
if "side" in params:
|
|
767
|
+
formula_inputs["side"] = height_value
|
|
762
768
|
|
|
763
769
|
value_idx = 0 # count how many values to be added in formula_inputs
|
|
764
770
|
for param in params:
|
|
771
|
+
if len(other_values) < 1:
|
|
772
|
+
break
|
|
765
773
|
if param == "height":
|
|
766
774
|
continue # already added
|
|
767
775
|
elif param == "other": # two consecutive numbers to append
|
|
@@ -770,6 +778,12 @@ class DLM:
|
|
|
770
778
|
else: # only one number to append
|
|
771
779
|
formula_inputs[param] = other_values[value_idx]
|
|
772
780
|
value_idx += 1
|
|
781
|
+
if len(other_values) <= 1:
|
|
782
|
+
break
|
|
783
|
+
|
|
784
|
+
if formula_inputs["height"] is None and len(other_values) > 1:
|
|
785
|
+
formula_inputs["height"] = other_values[len(other_values) - 1]
|
|
786
|
+
other_values.pop(len(other_values) - 1)
|
|
773
787
|
|
|
774
788
|
# Try calculating the result and return
|
|
775
789
|
result = round(formula(formula_inputs), 4)
|
|
@@ -789,8 +803,8 @@ class DLM:
|
|
|
789
803
|
Perform advanced Chain-of-Thought (CoT) reasoning to solve arithmetic or unit conversion problems.
|
|
790
804
|
|
|
791
805
|
Parameters:
|
|
792
|
-
filtered_query (str): The cleaned user input, expected to be a math
|
|
793
|
-
display_thought (bool): Indicates whether the user wants to have the bot display its thought process or just give the answer
|
|
806
|
+
filtered_query (str): The cleaned user input, expected to be a math or logic-based question.
|
|
807
|
+
display_thought (bool): Indicates whether the user wants to have the bot display its thought process or just give the answer.
|
|
794
808
|
|
|
795
809
|
Behavior:
|
|
796
810
|
- Simulates step-by-step reasoning to solve arithmetic word problems without relying on memorized answers.
|
|
@@ -819,8 +833,8 @@ class DLM:
|
|
|
819
833
|
if display_thought:
|
|
820
834
|
print(
|
|
821
835
|
f"{'\033[33m'}I am presented with a more involved query asking me to do some form of computation{'\033[0m'}")
|
|
822
|
-
self.
|
|
823
|
-
self.
|
|
836
|
+
self.__loading_animation("Let me think about this carefully and break it down so that I can solve it", 0.8)
|
|
837
|
+
self.__loading_animation(f"I’ve trimmed away any extra words so I’m focusing on \"{filtered_query}\" now",
|
|
824
838
|
0.8)
|
|
825
839
|
|
|
826
840
|
# Have the bot pick out names mentioned (in order) using SpaCy and NLTK (for maximum coverage)
|
|
@@ -1020,31 +1034,31 @@ class DLM:
|
|
|
1020
1034
|
if (not is_geometric_query) and (any(not lst for lst in (num_mentioned, operands_mentioned)) or (
|
|
1021
1035
|
'=' not in operands_mentioned and num_mentioned.__len__() < 2)): # don't compute if parts are missing
|
|
1022
1036
|
print(
|
|
1023
|
-
f"{self.
|
|
1037
|
+
f"{self.__loading_animation('Hmm', 0.8) or '' if display_thought else ''}{'\033[34m'}It looks like some essential details are missing, so I can’t complete this calculation right now.{'\033[0m'}")
|
|
1024
1038
|
print(
|
|
1025
1039
|
f"\033[34mIf you are asking a geometric query, try including geometric identifiers like \"{'\", \"'.join(geo_types)}\" in your query.\033[0m")
|
|
1026
1040
|
print(
|
|
1027
1041
|
f"\033[34mCurrently, I can only compute those identifiers aforementioned, but more geometric features are coming soon!\033[0m")
|
|
1028
1042
|
else: # else, the bot needs to explain what it has tokenized
|
|
1029
1043
|
if display_thought:
|
|
1030
|
-
self.
|
|
1044
|
+
self.__loading_animation(
|
|
1031
1045
|
f"1.) I see {', '.join(persons_mentioned) if persons_mentioned.__len__() >= 1 else 'no one'} mentioned as a person name; "
|
|
1032
1046
|
f"{'they’re likely key to this problem' if persons_mentioned.__len__() >= 1 else 'moving on'}", 0.2)
|
|
1033
|
-
self.
|
|
1047
|
+
self.__loading_animation(
|
|
1034
1048
|
f"2.) Moreover, I see {', '.join(items_mentioned) if items_mentioned.__len__() >= 1 else 'no items'} mentioned as proper nouns; "
|
|
1035
1049
|
f"{'this might be a key thing to this problem' if items_mentioned.__len__() >= 1 else 'moving on'}",
|
|
1036
1050
|
0.2)
|
|
1037
1051
|
if is_geometric_query:
|
|
1038
|
-
self.
|
|
1052
|
+
self.__loading_animation(f"3.) This is a geometric problem and I have already computed the answer",
|
|
1039
1053
|
0.2)
|
|
1040
1054
|
else:
|
|
1041
|
-
self.
|
|
1055
|
+
self.__loading_animation(
|
|
1042
1056
|
f"3.) I’ve also identified the numbers {' and '.join(num_mentioned)} that I need to compute with",
|
|
1043
1057
|
0.2)
|
|
1044
|
-
self.
|
|
1058
|
+
self.__loading_animation(
|
|
1045
1059
|
f"4.) I see the keywords \"{'\" and \"'.join(keywords_mentioned)}\", meaning I need to perform a \"{'\" and \"'.join(operands_mentioned)}\" operation for this query; I’ll use that to guide my calculation",
|
|
1046
1060
|
0.2)
|
|
1047
|
-
self.
|
|
1061
|
+
self.__loading_animation("Now I have the parts, so let me put it all together and solve", 0.3)
|
|
1048
1062
|
|
|
1049
1063
|
# Finally compute it and then give the response (if there is any)
|
|
1050
1064
|
# move "originally" numbers to the front
|
|
@@ -1154,7 +1168,7 @@ class DLM:
|
|
|
1154
1168
|
if source_key and target_key:
|
|
1155
1169
|
result = (num0 * self.__units[source_key]) / self.__units[target_key]
|
|
1156
1170
|
if display_thought:
|
|
1157
|
-
self.
|
|
1171
|
+
self.__loading_animation(
|
|
1158
1172
|
f"I need to take {num0} and multiply it by {self.__units[source_key]}. Finally, I divide by {self.__units[target_key]} and I got my answer",
|
|
1159
1173
|
0.2)
|
|
1160
1174
|
expr = f"{num_mentioned[0]} {source_key}(s) ==> {round(result, 2)} {target_key}(s)"
|
|
@@ -1203,7 +1217,7 @@ class DLM:
|
|
|
1203
1217
|
best_match_question (str): The closest matching question found in the knowledge base.
|
|
1204
1218
|
best_match_answer (str): The corresponding answer to the matched question.
|
|
1205
1219
|
highest_similarity (float): The calculated string similarity score (0 to 1) for the match.
|
|
1206
|
-
display_thought (bool): "True" if the bot is allowed to print its thought or else "False"
|
|
1220
|
+
display_thought (bool): "True" if the bot is allowed to print its thought or else "False".
|
|
1207
1221
|
|
|
1208
1222
|
Behavior:
|
|
1209
1223
|
- Outputs step-by-step reasoning in a conversational format (e.g., interpreting the question's structure and tone).
|
|
@@ -1223,7 +1237,7 @@ class DLM:
|
|
|
1223
1237
|
if self.__tone != "":
|
|
1224
1238
|
print(
|
|
1225
1239
|
f"{'\033[33m'}Right off the bat, the user seems quite {sentiment_tone[0]} or {sentiment_tone[1]} by their query tone. Hopefully I won't disappoint!{'\033[0m'}")
|
|
1226
|
-
if self.
|
|
1240
|
+
if self.__model == "compute":
|
|
1227
1241
|
self.__perform_advanced_CoT(filtered_query, display_thought)
|
|
1228
1242
|
else:
|
|
1229
1243
|
interrogative_start = filtered_query.split()[0]
|
|
@@ -1243,7 +1257,7 @@ class DLM:
|
|
|
1243
1257
|
else:
|
|
1244
1258
|
print(
|
|
1245
1259
|
f"{'\033[33m'}The user starts their query with \"{interrogative_start.title()}\" and they are asking about \"{" ".join(identifier).title()}\".{'\033[0m'}")
|
|
1246
|
-
self.
|
|
1260
|
+
self.__loading_animation("Let me think about this carefully", 0.8)
|
|
1247
1261
|
|
|
1248
1262
|
for s in special_start:
|
|
1249
1263
|
for u in filtered_query.split():
|
|
@@ -1264,7 +1278,7 @@ class DLM:
|
|
|
1264
1278
|
print(
|
|
1265
1279
|
f"{'\033[33m'}Furthermore, an in-depth vector analysis revealed a similarity percentage of {int(self.__nlp_similarity_value * 100)}%.{'\033[0m'}")
|
|
1266
1280
|
print(
|
|
1267
|
-
f"{self.
|
|
1281
|
+
f"{self.__loading_animation("Hmm", 0.8) or ''}{'\033[33m'}I don't think I know the answer, so I am going to let the user know that.{'\033[0m'}")
|
|
1268
1282
|
self.__unsure_while_thinking = True
|
|
1269
1283
|
else:
|
|
1270
1284
|
self.__unsure_while_thinking = False
|
|
@@ -1276,9 +1290,9 @@ class DLM:
|
|
|
1276
1290
|
if spacy_proceed:
|
|
1277
1291
|
print(
|
|
1278
1292
|
f"Additionally, doing a more in-depth vector NLP analysis resulted in {int(self.__nlp_similarity_value * 100)}% similarity. Although there are room for error, we will see.{'\033[0m'}")
|
|
1279
|
-
self.
|
|
1293
|
+
self.__loading_animation("Let me recall that answer", 0.8)
|
|
1280
1294
|
print("\n")
|
|
1281
|
-
elif self.
|
|
1295
|
+
elif self.__model == "compute":
|
|
1282
1296
|
self.__perform_advanced_CoT(filtered_query, display_thought)
|
|
1283
1297
|
|
|
1284
1298
|
def __generate_response(self, best_match_answer, best_match_question): # no return, void
|
|
@@ -1553,16 +1567,17 @@ class DLM:
|
|
|
1553
1567
|
NOTICE: To make the bot run continuously, implement a loop in your program.
|
|
1554
1568
|
|
|
1555
1569
|
Parameters:
|
|
1556
|
-
query (str): Question the bot would
|
|
1557
|
-
display_thought (bool): "True" for allowing bot to print its thought and CoT or "False"
|
|
1570
|
+
query (str): Question the bot would learn or respond to.
|
|
1571
|
+
display_thought (bool): "True" for allowing bot to print its thought and CoT or "False".
|
|
1558
1572
|
|
|
1559
1573
|
Behavior:
|
|
1560
1574
|
- Prompts the user for input.
|
|
1575
|
+
- Determines whether to choose "compute" or "memory" model to respond.
|
|
1561
1576
|
- Detects tone, filters input, searches knowledge base.
|
|
1562
1577
|
- Performs Chain-of-Thought (CoT) while recalling learnt answer.
|
|
1563
1578
|
- If match is found, generates a response.
|
|
1564
1579
|
- If in learning mode and answer is incorrect or not found, prompts user to teach the bot.
|
|
1565
|
-
- In
|
|
1580
|
+
- In apply mode, automatically chooses between its compute and memory model to answer the query.
|
|
1566
1581
|
"""
|
|
1567
1582
|
self.__query = query
|
|
1568
1583
|
while self.__query is None or self.__query == "":
|
|
@@ -1576,9 +1591,18 @@ class DLM:
|
|
|
1576
1591
|
self.__query = input("Empty input is unacceptable. Please enter something: ")
|
|
1577
1592
|
self.__set_sentiment_tone(self.__query)
|
|
1578
1593
|
|
|
1594
|
+
# auto model choose using HuggingFace
|
|
1595
|
+
if self.__mode != "learn":
|
|
1596
|
+
auto_model_choice = self.__hf_classifier(self.__query, ["mathematical", "not mathematical"])["labels"][0]
|
|
1597
|
+
if auto_model_choice == "mathematical":
|
|
1598
|
+
self.__model = "compute"
|
|
1599
|
+
else:
|
|
1600
|
+
self.__model = "memory"
|
|
1601
|
+
else:
|
|
1602
|
+
self.__model = "memory"
|
|
1579
1603
|
|
|
1580
1604
|
# storing the user-query (filtered, lower-case, no punctuation)
|
|
1581
|
-
if self.
|
|
1605
|
+
if self.__model == "compute":
|
|
1582
1606
|
# We want to keep the following
|
|
1583
1607
|
keep = {".", "+", "-", "*", "/", "="}
|
|
1584
1608
|
to_remove = "".join(ch for ch in string.punctuation if ch not in keep)
|
|
@@ -1586,9 +1610,7 @@ class DLM:
|
|
|
1586
1610
|
to_remove = string.punctuation
|
|
1587
1611
|
|
|
1588
1612
|
translation_table = str.maketrans("", "", to_remove)
|
|
1589
|
-
filtered_query = self.__filtered_input(
|
|
1590
|
-
self.__query.lower().translate(translation_table)
|
|
1591
|
-
)
|
|
1613
|
+
filtered_query = self.__filtered_input(self.__query.lower().translate(translation_table))
|
|
1592
1614
|
|
|
1593
1615
|
# match_query is the query without special words to prevent interference with SpaCy similarity
|
|
1594
1616
|
self.__special_stripped_query = filtered_query
|
|
@@ -1626,7 +1648,7 @@ class DLM:
|
|
|
1626
1648
|
display_thought)
|
|
1627
1649
|
|
|
1628
1650
|
# accept a match if highest_similarity is 65% or more, or if semantic similarity is recognized
|
|
1629
|
-
if self.
|
|
1651
|
+
if self.__model == "memory":
|
|
1630
1652
|
if (not self.__unsure_while_thinking) and ((highest_similarity >= 0.65) or (
|
|
1631
1653
|
best_match_answer and self.__semantic_similarity(self.__special_stripped_query,
|
|
1632
1654
|
best_match_question))):
|
|
@@ -1663,5 +1685,5 @@ class DLM:
|
|
|
1663
1685
|
self.__learn(self.__expectation,
|
|
1664
1686
|
self.__category) # learn this new question and answer pair and add to knowledgebase
|
|
1665
1687
|
print("I learned something new!") # confirmation that it went through the whole process
|
|
1666
|
-
else: # only executes when in
|
|
1688
|
+
else: # only executes when in apply mode and bot cannot find the answer
|
|
1667
1689
|
print(f"{'\033[34m'}{random.choice(self.__fallback_responses)}{'\033[0m'}")
|
{dynamic_learning_model-2.1 → dynamic_learning_model-3.0/dynamic_learning_model.egg-info}/PKG-INFO
RENAMED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: dynamic-learning-model
|
|
3
|
-
Version:
|
|
3
|
+
Version: 3.0
|
|
4
4
|
Summary: A Dynamic Learning Model for processing NLP queries using hybrid AI and reasoning.
|
|
5
5
|
Home-page: https://github.com/VigneshT24/Dynamic_Learning_Model
|
|
6
6
|
Author: Vignesh Thondikulam
|
|
@@ -16,6 +16,7 @@ Requires-Dist: nltk
|
|
|
16
16
|
Requires-Dist: spacy
|
|
17
17
|
Requires-Dist: better_profanity
|
|
18
18
|
Requires-Dist: word2number
|
|
19
|
+
Requires-Dist: transformers
|
|
19
20
|
Dynamic: author
|
|
20
21
|
Dynamic: author-email
|
|
21
22
|
Dynamic: classifier
|
|
@@ -30,6 +31,7 @@ Dynamic: summary
|
|
|
30
31
|
|
|
31
32
|

|
|
32
33
|

|
|
34
|
+

|
|
33
35
|
|
|
34
36
|
# Dynamic Learning Model
|
|
35
37
|
**ABOUT**:
|
|
@@ -50,8 +52,7 @@ Whether you're building a student support bot, a domain-specific assistant, or a
|
|
|
50
52
|
* The constructor requires passing in two parameters:
|
|
51
53
|
- Bot Mode:
|
|
52
54
|
- 'learn' = Enables training using the memory model. The bot can be updated with new information,
|
|
53
|
-
- '
|
|
54
|
-
- 'compute' = Activates the computation model for processing and solving queries algorithmically (no training)
|
|
55
|
+
- 'apply' = The bot automatically switches between its "compute" and "memory" model depending on the query asked
|
|
55
56
|
- Empty SQL Database for training the bot with queries and for the memory model
|
|
56
57
|
* The ask() method also requires passing in two parameters:
|
|
57
58
|
- Query: "What is the definition of FAFSA" (as an example)
|
|
@@ -74,22 +75,17 @@ training_bot = DLM("learn", "college_knowledge.db")
|
|
|
74
75
|
training_bot.ask("What is FAFSA in college?", True)
|
|
75
76
|
```
|
|
76
77
|
|
|
77
|
-
('
|
|
78
|
+
('apply' mode [deployment/production use after training])
|
|
78
79
|
```python
|
|
79
80
|
from dlm import DLM
|
|
80
81
|
|
|
81
|
-
commercial_bot = DLM("
|
|
82
|
+
commercial_bot = DLM("apply", "college_knowledge.db")
|
|
82
83
|
|
|
83
84
|
commercial_bot.ask("What is the difference between FAFSA and CADAA in California?", False)
|
|
84
|
-
```
|
|
85
|
-
|
|
86
|
-
('compute' mode [computation queries])
|
|
87
|
-
```python
|
|
88
|
-
from dlm import DLM
|
|
89
85
|
|
|
90
|
-
|
|
86
|
+
# or
|
|
91
87
|
|
|
92
|
-
|
|
88
|
+
commercial_bot.ask("Tell me the result for the following: 5 * 5 * 5 + 5 / 5", True)
|
|
93
89
|
```
|
|
94
90
|
|
|
95
91
|
**HIGH-LEVEL PIPELINE VISUAL**:
|
|
@@ -5,7 +5,7 @@ with open('README.md', 'r', encoding='utf-8') as f:
|
|
|
5
5
|
|
|
6
6
|
setup(
|
|
7
7
|
name='dynamic-learning-model',
|
|
8
|
-
version='
|
|
8
|
+
version='3.0',
|
|
9
9
|
author='Vignesh Thondikulam',
|
|
10
10
|
author_email='vignesh.tho2006@gmail.com',
|
|
11
11
|
description='A Dynamic Learning Model for processing NLP queries using hybrid AI and reasoning.',
|
|
@@ -18,7 +18,8 @@ setup(
|
|
|
18
18
|
'nltk',
|
|
19
19
|
'spacy',
|
|
20
20
|
'better_profanity',
|
|
21
|
-
'word2number'
|
|
21
|
+
'word2number',
|
|
22
|
+
'transformers'
|
|
22
23
|
],
|
|
23
24
|
classifiers=[
|
|
24
25
|
'Programming Language :: Python :: 3',
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|