Spaces:
Sleeping
Sleeping
Commit
·
71fa3d9
1
Parent(s):
fbdb959
better query calc
Browse files- analyze_verses_universal.py +80 -52
analyze_verses_universal.py
CHANGED
@@ -9,68 +9,93 @@ from deep_translator import GoogleTranslator
|
|
9 |
from gematria import calculate_gematria
|
10 |
from collections import defaultdict
|
11 |
|
12 |
-
# ---
|
13 |
logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(levelname)s - %(message)s')
|
14 |
BOOK_RANGE = range(1, 40)
|
15 |
CACHE_FILE = "tanakh_phrasedict.cache"
|
16 |
|
17 |
-
# ---
|
|
|
18 |
def get_power_result(total_sum, query_value):
|
19 |
-
"""
|
|
|
|
|
|
|
|
|
20 |
if total_sum <= 0 or query_value <= 1:
|
21 |
return 1
|
22 |
-
elif query_value > total_sum:
|
23 |
-
return math.ceil(math.sqrt(query_value))
|
24 |
|
25 |
-
|
26 |
-
|
27 |
-
|
28 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
29 |
return 1
|
30 |
|
31 |
def load_phrase_dictionary():
|
32 |
if not os.path.exists(CACHE_FILE):
|
33 |
-
sys.exit(f"
|
34 |
-
logging.info(f"
|
35 |
try:
|
36 |
with open(CACHE_FILE, 'rb') as f:
|
37 |
return pickle.load(f)
|
38 |
except Exception as e:
|
39 |
-
sys.exit(f"
|
40 |
|
41 |
def find_all_matching_phrases(target_sum, phrase_dictionary):
|
42 |
-
return phrase_dictionary.get(target_sum, [])
|
43 |
|
44 |
-
# ---
|
45 |
def main(args):
|
46 |
phrase_dictionary = load_phrase_dictionary()
|
47 |
query_value = calculate_gematria(args.query)
|
48 |
if query_value <= 1:
|
49 |
-
sys.exit(f"
|
50 |
|
51 |
translator = None
|
52 |
if args.translate:
|
53 |
try:
|
|
|
54 |
translator = GoogleTranslator(source='iw', target='en')
|
55 |
except Exception as e:
|
56 |
-
logging.error(f"
|
57 |
|
58 |
-
logging.info(f"
|
59 |
-
print("\n" + "="*20 + f"
|
60 |
|
61 |
verses_processed = 0
|
62 |
resonance_count = 0
|
63 |
|
64 |
for book_num in BOOK_RANGE:
|
65 |
if args.process_verses and verses_processed >= args.process_verses: break
|
66 |
-
|
67 |
filepath = f"texts/torah/{book_num:02}.json"
|
68 |
try:
|
69 |
with open(filepath, 'r', encoding='utf-8') as file:
|
70 |
data = json.load(file)
|
71 |
for chap_idx, chapter in enumerate(data.get("text", []), start=1):
|
72 |
if args.process_verses and verses_processed >= args.process_verses: break
|
73 |
-
|
74 |
for verse_idx, verse_text in enumerate(chapter, start=1):
|
75 |
if args.process_verses and verses_processed >= args.process_verses: break
|
76 |
verses_processed += 1
|
@@ -79,69 +104,72 @@ def main(args):
|
|
79 |
if verse_sum <= 1: continue
|
80 |
|
81 |
power_result = get_power_result(verse_sum, query_value)
|
82 |
-
|
83 |
-
#
|
84 |
main_target_sum = verse_sum ^ power_result
|
85 |
main_matches = find_all_matching_phrases(main_target_sum, phrase_dictionary)
|
86 |
|
87 |
-
#
|
88 |
if not main_matches:
|
89 |
continue
|
90 |
|
91 |
resonance_count += 1
|
92 |
-
verse_ref = f"B{book_num:02d},
|
93 |
-
print(f"\n---
|
94 |
-
print(f"
|
95 |
-
|
96 |
def print_matches(matches, title, calculation_str):
|
97 |
if not matches: return
|
98 |
-
|
99 |
matches.sort(key=lambda p: (p.get('freq', 0) / p.get('words', 99)), reverse=True)
|
100 |
matches_to_show = matches[:args.results_per_verse]
|
101 |
|
102 |
print(f" ↳ {title}: {calculation_str}")
|
103 |
-
|
104 |
for match in matches_to_show:
|
105 |
translation_str = ""
|
106 |
if translator:
|
107 |
-
try:
|
108 |
-
|
|
|
|
|
109 |
|
110 |
score = (match.get('freq', 0) / match.get('words', 99))
|
111 |
-
info = f"(
|
112 |
print(f" - {match['text']} {info}")
|
113 |
if translation_str:
|
114 |
print(f" ↳ Interpretation: \"{translation_str}\"")
|
115 |
|
116 |
-
# 1.
|
117 |
-
calc_str = f"[{verse_sum}] ^ [{power_result}] → [
|
118 |
-
print_matches(main_matches, "
|
119 |
-
|
120 |
-
# 2.
|
121 |
if args.xor_depth > 0:
|
122 |
-
print(f" [INFO] Bitplane
|
123 |
for depth in range(args.xor_depth):
|
124 |
bit_flip = 1 << depth
|
125 |
-
|
126 |
-
#
|
127 |
target_sum = main_target_sum ^ bit_flip
|
128 |
-
|
129 |
bitplane_matches = find_all_matching_phrases(target_sum, phrase_dictionary)
|
130 |
-
|
131 |
if bitplane_matches:
|
132 |
-
|
133 |
-
|
134 |
-
|
|
|
135 |
except FileNotFoundError: continue
|
136 |
|
137 |
-
logging.info(f"
|
138 |
|
139 |
if __name__ == "__main__":
|
140 |
-
parser = argparse.ArgumentParser(description="Tanakh Universal Resonance Analyzer
|
141 |
-
parser.add_argument("query", type=str, help="
|
142 |
-
parser.add_argument("--translate", action="store_true", help="
|
143 |
-
parser.add_argument("--process-verses", type=int, default=10, help="
|
144 |
-
parser.add_argument("--results-per-verse", type=int, default=
|
145 |
-
parser.add_argument("--xor-depth", type=int, default=
|
146 |
args = parser.parse_args()
|
147 |
main(args)
|
|
|
9 |
from gematria import calculate_gematria
|
10 |
from collections import defaultdict
|
11 |
|
12 |
+
# --- Configuration ---
|
13 |
logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(levelname)s - %(message)s')
|
14 |
BOOK_RANGE = range(1, 40)
|
15 |
CACHE_FILE = "tanakh_phrasedict.cache"
|
16 |
|
17 |
+
# --- Core Functions ---
|
18 |
+
|
19 |
def get_power_result(total_sum, query_value):
|
20 |
+
"""
|
21 |
+
Calculates the power or root result.
|
22 |
+
- If query_value <= total_sum, it finds the highest power of query_value that is <= total_sum.
|
23 |
+
- If query_value > total_sum, it finds the smallest n-th root of query_value whose result is <= total_sum.
|
24 |
+
"""
|
25 |
if total_sum <= 0 or query_value <= 1:
|
26 |
return 1
|
|
|
|
|
27 |
|
28 |
+
# Normal case: "Power Mode"
|
29 |
+
if query_value <= total_sum:
|
30 |
+
try:
|
31 |
+
exponent = int(math.floor(math.log(total_sum, query_value)))
|
32 |
+
return query_value ** exponent
|
33 |
+
except (ValueError, OverflowError):
|
34 |
+
return 1
|
35 |
+
|
36 |
+
# Special case: "Root Mode"
|
37 |
+
else: # query_value > total_sum
|
38 |
+
# Find the smallest integer root 'n' (starting from 2)
|
39 |
+
# that reduces query_value to a number <= total_sum.
|
40 |
+
for n in range(2, 65): # Limit the search to a reasonable range (up to the 64th root)
|
41 |
+
try:
|
42 |
+
root_result = query_value ** (1.0 / n)
|
43 |
+
if root_result <= total_sum:
|
44 |
+
# We found the smallest root exponent n.
|
45 |
+
# Round up and return as an integer.
|
46 |
+
return math.ceil(root_result)
|
47 |
+
except (ValueError, OverflowError):
|
48 |
+
# Catches math errors with extreme numbers
|
49 |
+
return 1
|
50 |
+
|
51 |
+
# If even the 64th root is too large, which only happens with
|
52 |
+
# extreme number ratios, return a default value.
|
53 |
return 1
|
54 |
|
55 |
def load_phrase_dictionary():
|
56 |
if not os.path.exists(CACHE_FILE):
|
57 |
+
sys.exit(f"ERROR: Cache file '{CACHE_FILE}' not found. Please run 'build_indices.py' first to create the index.")
|
58 |
+
logging.info(f"Loading phrase dictionary from cache: {CACHE_FILE}")
|
59 |
try:
|
60 |
with open(CACHE_FILE, 'rb') as f:
|
61 |
return pickle.load(f)
|
62 |
except Exception as e:
|
63 |
+
sys.exit(f"ERROR: Cache file '{CACHE_FILE}' is corrupt. Please delete it and run 'build_indices.py' again. Error: {e}")
|
64 |
|
65 |
def find_all_matching_phrases(target_sum, phrase_dictionary):
|
66 |
+
return phrase_dictionary.get(int(target_sum), [])
|
67 |
|
68 |
+
# --- Main Program ---
|
69 |
def main(args):
|
70 |
phrase_dictionary = load_phrase_dictionary()
|
71 |
query_value = calculate_gematria(args.query)
|
72 |
if query_value <= 1:
|
73 |
+
sys.exit(f"ERROR: Query '{args.query}' has an invalid Gematria value ({query_value}).")
|
74 |
|
75 |
translator = None
|
76 |
if args.translate:
|
77 |
try:
|
78 |
+
# The correct code for Hebrew is 'iw'
|
79 |
translator = GoogleTranslator(source='iw', target='en')
|
80 |
except Exception as e:
|
81 |
+
logging.error(f"Could not initialize translator: {e}")
|
82 |
|
83 |
+
logging.info(f"Starting oracle analysis for '{args.query}' (G:{query_value}) with bitplane variation depth {args.xor_depth}...")
|
84 |
+
print("\n" + "="*20 + f" ORACLE ANSWERS FOR '{args.query}' " + "="*20)
|
85 |
|
86 |
verses_processed = 0
|
87 |
resonance_count = 0
|
88 |
|
89 |
for book_num in BOOK_RANGE:
|
90 |
if args.process_verses and verses_processed >= args.process_verses: break
|
91 |
+
|
92 |
filepath = f"texts/torah/{book_num:02}.json"
|
93 |
try:
|
94 |
with open(filepath, 'r', encoding='utf-8') as file:
|
95 |
data = json.load(file)
|
96 |
for chap_idx, chapter in enumerate(data.get("text", []), start=1):
|
97 |
if args.process_verses and verses_processed >= args.process_verses: break
|
98 |
+
|
99 |
for verse_idx, verse_text in enumerate(chapter, start=1):
|
100 |
if args.process_verses and verses_processed >= args.process_verses: break
|
101 |
verses_processed += 1
|
|
|
104 |
if verse_sum <= 1: continue
|
105 |
|
106 |
power_result = get_power_result(verse_sum, query_value)
|
107 |
+
|
108 |
+
# Calculate the main result first
|
109 |
main_target_sum = verse_sum ^ power_result
|
110 |
main_matches = find_all_matching_phrases(main_target_sum, phrase_dictionary)
|
111 |
|
112 |
+
# Only proceed if a main resonance exists
|
113 |
if not main_matches:
|
114 |
continue
|
115 |
|
116 |
resonance_count += 1
|
117 |
+
verse_ref = f"B{book_num:02d}, C{chap_idx}, V{verse_idx}"
|
118 |
+
print(f"\n--- Resonance #{resonance_count} in [{verse_ref}] (G_sum:{verse_sum}) ---")
|
119 |
+
print(f"Original Verse: {verse_text.strip()}")
|
120 |
+
|
121 |
def print_matches(matches, title, calculation_str):
|
122 |
if not matches: return
|
123 |
+
|
124 |
matches.sort(key=lambda p: (p.get('freq', 0) / p.get('words', 99)), reverse=True)
|
125 |
matches_to_show = matches[:args.results_per_verse]
|
126 |
|
127 |
print(f" ↳ {title}: {calculation_str}")
|
128 |
+
|
129 |
for match in matches_to_show:
|
130 |
translation_str = ""
|
131 |
if translator:
|
132 |
+
try:
|
133 |
+
translation_str = translator.translate(match['text'])
|
134 |
+
except Exception:
|
135 |
+
translation_str = "[Translation failed]"
|
136 |
|
137 |
score = (match.get('freq', 0) / match.get('words', 99))
|
138 |
+
info = f"(Words: {match.get('words', 'N/A')}, Freq: {match.get('freq', 'N/A')}, Score: {score:.2f})"
|
139 |
print(f" - {match['text']} {info}")
|
140 |
if translation_str:
|
141 |
print(f" ↳ Interpretation: \"{translation_str}\"")
|
142 |
|
143 |
+
# 1. Display the main resonance
|
144 |
+
calc_str = f"[{verse_sum}] ^ [{power_result}] → [G_target:{main_target_sum}]"
|
145 |
+
print_matches(main_matches, "Main Resonance", calc_str)
|
146 |
+
|
147 |
+
# 2. Display the bitplane variations of the RESULT
|
148 |
if args.xor_depth > 0:
|
149 |
+
print(f" [INFO] Bitplane Variations of the Result ({main_target_sum}):")
|
150 |
for depth in range(args.xor_depth):
|
151 |
bit_flip = 1 << depth
|
152 |
+
|
153 |
+
# Flip the 'd'-th bit in the main result
|
154 |
target_sum = main_target_sum ^ bit_flip
|
155 |
+
|
156 |
bitplane_matches = find_all_matching_phrases(target_sum, phrase_dictionary)
|
157 |
+
|
158 |
if bitplane_matches:
|
159 |
+
# FIX: The label is now depth + 1 for human readability
|
160 |
+
bitplane_calc_str = f"[{main_target_sum}] ^ [Bit {depth+1}] → [G_target:{target_sum}]"
|
161 |
+
print_matches(bitplane_matches, f"Variation (Depth {depth + 1})", bitplane_calc_str)
|
162 |
+
|
163 |
except FileNotFoundError: continue
|
164 |
|
165 |
+
logging.info(f"Analysis complete. Found {resonance_count} resonance groups in {verses_processed} analyzed verses.")
|
166 |
|
167 |
if __name__ == "__main__":
|
168 |
+
parser = argparse.ArgumentParser(description="Tanakh Universal Resonance Analyzer with Bitplane Variations.")
|
169 |
+
parser.add_argument("query", type=str, help="The query phrase (e.g., 'יהוה').")
|
170 |
+
parser.add_argument("--translate", action="store_true", default=True, help="Enable automatic translation of results to English.")
|
171 |
+
parser.add_argument("--process-verses", type=int, default=10, help="Maximum number of starting verses to analyze.")
|
172 |
+
parser.add_argument("--results-per-verse", type=int, default=1, help="Maximum oracle answers to show per resonance type (default: 3).")
|
173 |
+
parser.add_argument("--xor-depth", type=int, default=2, help="Maximum depth for bitplane variations of the result (0-15) (default: 16).")
|
174 |
args = parser.parse_args()
|
175 |
main(args)
|