Skip to content

Commit 3c44af7

Browse files
committed
updating run.py
1 parent 5773c86 commit 3c44af7

File tree

5 files changed

+175
-156
lines changed

5 files changed

+175
-156
lines changed

scripts/profiling.py

Lines changed: 32 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -10,14 +10,17 @@
1010
QR,
1111
QR_cp,
1212
)
13-
from pyclassify.utils import make_symmetric, read_config
13+
from pyclassify.utils import (
14+
make_symmetric,
15+
read_config,
16+
profile_with_cprofile,
17+
profile_with_cupy_profiler,
18+
)
1419
import numpy as np
1520
import scipy.sparse as sp
21+
import scipy
1622
import random
1723
import argparse
18-
import cProfile
19-
import os
20-
import csv
2124

2225

2326
seed = 8422
@@ -34,80 +37,50 @@
3437
args.config if args.config else "./experiments/config"
3538
) # automatic choice if no argument is passed
3639

40+
3741
kwargs = read_config(filename)
3842
dim = kwargs["dim"]
3943
density = kwargs["density"]
4044
tol = kwargs["tol"]
4145
max_iter = kwargs["max_iter"]
4246

4347

44-
matrix = sp.random(dim, dim, density=density, format="coo")
45-
matrix = make_symmetric(matrix)
46-
cp_symm_matrix = cpsp.csr_matrix(matrix)
48+
eigenvals = np.arange(1, dim + 1)
49+
A = np.diag(eigenvals)
50+
U = scipy.stats.ortho_group.rvs(dim)
51+
A = U @ A @ U.T
52+
A = make_symmetric(A)
53+
A = sp.csr_matrix(A)
54+
A_cp = cpsp.csr_matrix(A)
4755

4856

49-
logs = "./logs"
57+
log_file = "./logs/timings.csv"
5058
iteration_factor = 300
5159

5260

53-
def profile_with_cprofile(func_name, func, *args, **kwargs):
54-
log_file = "./logs/timings.csv"
55-
with open(log_file, "a", newline="") as csvfile:
56-
writer = csv.writer(csvfile)
57-
58-
profile_output = cProfile.Profile()
59-
profile_output.enable()
60-
61-
result = func(*args, **kwargs)
62-
63-
profile_output.disable()
64-
65-
stats = profile_output.getstats()
66-
total_time = sum(stat.totaltime for stat in stats)
67-
68-
print(f"{func_name}: {total_time:.6f} s")
69-
70-
writer.writerow([func_name, dim, total_time])
71-
72-
return result
73-
74-
7561
profile_with_cprofile(
76-
"eigenvalues_np", eigenvalues_np, matrix.toarray(), symmetric=True
62+
log_file, dim, "eigenvalues_np", eigenvalues_np, A.toarray(), symmetric=True
63+
)
64+
profile_with_cprofile(
65+
log_file, dim, "eigenvalues_sp", eigenvalues_sp, A, symmetric=True
66+
)
67+
profile_with_cprofile(log_file, dim, "power_method", power_method, A)
68+
profile_with_cprofile(
69+
log_file, dim, "power_method_numba", power_method_numba, A.toarray()
70+
)
71+
profile_with_cprofile(
72+
log_file, dim, "QR", QR, A.toarray(), max_iter=iteration_factor * dim
7773
)
78-
profile_with_cprofile("eigenvalues_sp", eigenvalues_sp, matrix, symmetric=True)
79-
profile_with_cprofile("power_method", power_method, matrix)
80-
profile_with_cprofile("power_method_numba", power_method_numba, matrix.toarray())
81-
profile_with_cprofile("QR", QR, matrix.toarray(), max_iter=iteration_factor * dim)
82-
83-
84-
def profile_with_cupy_profiler(func_name, func, *args, **kwargs):
85-
log_file = "./logs/timings.csv"
86-
with open(log_file, "a", newline="") as csvfile:
87-
writer = csv.writer(csvfile)
88-
start = cp.cuda.Event()
89-
end = cp.cuda.Event()
90-
91-
start.record()
92-
result = func(*args, **kwargs)
93-
end.record()
94-
end.synchronize()
95-
96-
result = func(*args, **kwargs)
97-
elapsed_time = cp.cuda.get_elapsed_time(start, end) / 1000
98-
print(f"{func_name}: {elapsed_time:.6f} s")
99-
100-
writer.writerow([func_name, dim, elapsed_time])
101-
102-
return result
10374

10475

105-
profile_with_cupy_profiler("eigenvalues_cp", eigenvalues_cp, cp_symm_matrix)
106-
profile_with_cupy_profiler("power_method_cp", power_method_cp, cp_symm_matrix)
76+
profile_with_cupy_profiler(log_file, dim, "eigenvalues_cp", eigenvalues_cp, A_cp)
77+
profile_with_cupy_profiler(log_file, dim, "power_method_cp", power_method_cp, A_cp)
10778
profile_with_cupy_profiler(
79+
log_file,
80+
dim,
10881
"QR_cp",
10982
QR_cp,
110-
cp_symm_matrix,
83+
A_cp,
11184
q0=cp.random.rand(dim),
11285
tol=1e-3,
11386
max_iter=iteration_factor * dim,

scripts/run.py

Lines changed: 91 additions & 92 deletions
Original file line numberDiff line numberDiff line change
@@ -1,92 +1,91 @@
1-
import cupyx.scipy.sparse as cpsp
2-
import cupy as cp
3-
from pyclassify import (
4-
eigenvalues_np,
5-
eigenvalues_sp,
6-
eigenvalues_cp,
7-
power_method,
8-
power_method_numba,
9-
power_method_cp,
10-
QR,
11-
QR_cp,
12-
)
13-
from pyclassify.utils import make_symmetric, read_config
14-
import numpy as np
15-
import scipy.sparse as sp
16-
import random
17-
import argparse
18-
import cProfile
19-
import cupyx.profiler as profiler
20-
import os
21-
import csv
22-
23-
24-
random.seed(226)
25-
cp.random.seed(226)
26-
np.random.seed(226)
27-
28-
29-
parser = argparse.ArgumentParser()
30-
parser.add_argument("--config", type=str, required=False, help="config file:")
31-
32-
33-
args = parser.parse_args()
34-
filename = (
35-
args.config if args.config else "./experiments/config"
36-
) # automatic choice if no argument is passed
37-
38-
39-
kwargs = read_config(filename)
40-
dim = kwargs["dim"]
41-
density = kwargs["density"]
42-
tol = kwargs["tol"]
43-
max_iter = kwargs["max_iter"]
44-
45-
46-
matrix = sp.random(dim, dim, density=density, format="csr")
47-
matrix = make_symmetric(matrix)
48-
cp_symm_matrix = cpsp.csr_matrix(matrix)
49-
50-
51-
logs = "./logs"
52-
iteration_factor = 300
53-
54-
55-
cProfile.run(
56-
"eigenvalues_np(matrix.toarray(), symmetric=True)",
57-
os.path.join(logs, f"eigenvalues_np_{dim}.prof"),
58-
)
59-
cProfile.run(
60-
"eigenvalues_np(matrix, symmetric=True)",
61-
os.path.join(logs, f"eigenvalues_sp_{dim}.prof"),
62-
)
63-
cProfile.run("power_method(matrix)", os.path.join(logs, f"power_method_{dim}.prof"))
64-
cProfile.run(
65-
"power_method(matrix.toarray())",
66-
os.path.join(logs, f"power_method_numba{dim}.prof"),
67-
)
68-
cProfile.run(
69-
"QR(matrix.toarray(), max_iter=iteration_factor*d)",
70-
os.path.join(logs, f"QR_{dim}.prof"),
71-
)
72-
73-
74-
def profile_function(func_name, func, *args, **kwargs):
75-
cupyx.profiler.start()
76-
result = func(*args, **kwargs)
77-
cupyx.profiler.stop()
78-
79-
profiler_data = cupyx.profiler.get_profiler()
80-
81-
output_file = os.path.join(logs, f"{func_name}_{dim}.prof")
82-
with open(output_file, "w") as f:
83-
f.write(str(profiler_data))
84-
85-
elapsed_time = profiler_data[0]["time"]
86-
print(f"{func_name}: {elapsed_time/1000} s")
87-
return result
88-
89-
90-
profile_function("eigenvalues_cp", eigenvalues_cp, cp_symm_matrix)
91-
profile_function("power_method_cp", power_method_cp, cp_symm_matrix)
92-
profile_function("QR_cp", QR_cp, cp_symm_matrix, max_iter=iteration_factor * d)
1+
import cupyx.scipy.sparse as cpsp
2+
import cupy as cp
3+
from pyclassify import (
4+
eigenvalues_np,
5+
eigenvalues_sp,
6+
eigenvalues_cp,
7+
power_method,
8+
power_method_numba,
9+
power_method_cp,
10+
QR,
11+
QR_cp,
12+
)
13+
from pyclassify.utils import (
14+
make_symmetric,
15+
read_config,
16+
profile_with_cprofile,
17+
profile_with_cupy_profiler,
18+
)
19+
import numpy as np
20+
import scipy.sparse as sp
21+
import scipy
22+
import random
23+
import argparse
24+
25+
26+
cp.cuda.Device(0).use()
27+
cp.get_default_memory_pool().free_all_blocks()
28+
29+
30+
seed = 8422
31+
random.seed(seed)
32+
cp.random.seed(seed)
33+
np.random.seed(seed)
34+
35+
36+
parser = argparse.ArgumentParser()
37+
parser.add_argument("--config", type=str, required=False, help="config file:")
38+
39+
args = parser.parse_args()
40+
filename = (
41+
args.config if args.config else "./experiments/config"
42+
) # automatic choice if no argument is passed
43+
44+
45+
kwargs = read_config(filename)
46+
dim = kwargs["dim"]
47+
density = kwargs["density"]
48+
tol = kwargs["tol"]
49+
max_iter = kwargs["max_iter"]
50+
51+
52+
eigenvals = np.arange(1, dim + 1)
53+
A = np.diag(eigenvals)
54+
U = scipy.stats.ortho_group.rvs(dim)
55+
A = U @ A @ U.T
56+
A = make_symmetric(A)
57+
A = sp.csr_matrix(A)
58+
A_cp = cpsp.csr_matrix(A)
59+
60+
61+
log_file = "./logs/timings.csv"
62+
iteration_factor = 300
63+
64+
65+
profile_with_cprofile(
66+
log_file, dim, "eigenvalues_np", eigenvalues_np, A.toarray(), symmetric=True
67+
)
68+
profile_with_cprofile(
69+
log_file, dim, "eigenvalues_sp", eigenvalues_sp, A, symmetric=True
70+
)
71+
profile_with_cprofile(log_file, dim, "power_method", power_method, A)
72+
profile_with_cprofile(
73+
log_file, dim, "power_method_numba", power_method_numba, A.toarray()
74+
)
75+
profile_with_cprofile(
76+
log_file, dim, "QR", QR, A.toarray(), max_iter=iteration_factor * dim
77+
)
78+
79+
80+
profile_with_cupy_profiler(log_file, dim, "eigenvalues_cp", eigenvalues_cp, A_cp)
81+
profile_with_cupy_profiler(log_file, dim, "power_method_cp", power_method_cp, A_cp)
82+
profile_with_cupy_profiler(
83+
log_file,
84+
dim,
85+
"QR_cp",
86+
QR_cp,
87+
A_cp,
88+
q0=cp.random.rand(dim),
89+
tol=1e-3,
90+
max_iter=iteration_factor * dim,
91+
)

shell/submit.sbatch

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ for dim in 100 500 1000; do
4646
echo "tol: $tol" >> experiments/config.yaml
4747
echo "max_iter: $max_iter" >> experiments/config.yaml
4848

49-
python scripts/profiling.py
49+
python scripts/run.py
5050

5151
echo "dim: $dim - times saved in logs/timings.csv"
5252
echo '--------------------------------------------------'

src/pyclassify/eigenvalues.py

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -391,7 +391,6 @@ def QR_method(diag, off_diag, tol=1e-8, max_iter=1000):
391391
iter += 1
392392
if abs(off_diag[m - 1]) < tol * (np.abs(diag[m]) + np.abs(diag[m - 1])):
393393
m -= 1
394-
395394
return diag, Q
396395

397396

src/pyclassify/utils.py

Lines changed: 51 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,11 @@
55
import numba
66
import os
77
import yaml
8-
from line_profiler import profile
98

10-
11-
# from numba.pycc import CC
9+
# from line_profiler import profile
10+
import cProfile
11+
import cupyx.profiler as profiler
12+
import csv
1213

1314

1415
def check_square_matrix(A):
@@ -136,3 +137,50 @@ def read_config(file: str) -> dict:
136137
with open(filepath, "r") as stream:
137138
kwargs = yaml.safe_load(stream)
138139
return kwargs
140+
141+
142+
def profile_with_cprofile(log_file, dim, func_name, func, *args, **kwargs):
143+
"""
144+
Function used to profile the code using cProfile.
145+
"""
146+
with open(log_file, "a", newline="") as csvfile:
147+
writer = csv.writer(csvfile)
148+
149+
profile_output = cProfile.Profile()
150+
profile_output.enable()
151+
152+
result = func(*args, **kwargs)
153+
154+
profile_output.disable()
155+
156+
stats = profile_output.getstats()
157+
total_time = sum(stat.totaltime for stat in stats)
158+
159+
print(f"{func_name}: {total_time:.6f} s")
160+
161+
writer.writerow([func_name, dim, total_time])
162+
163+
return result
164+
165+
166+
def profile_with_cupy_profiler(log_file, dim, func_name, func, *args, **kwargs):
167+
"""
168+
Function used to profile the code using the CuPy profiler.
169+
"""
170+
with open(log_file, "a", newline="") as csvfile:
171+
writer = csv.writer(csvfile)
172+
start = cp.cuda.Event()
173+
end = cp.cuda.Event()
174+
175+
start.record()
176+
result = func(*args, **kwargs)
177+
end.record()
178+
end.synchronize()
179+
180+
result = func(*args, **kwargs)
181+
elapsed_time = cp.cuda.get_elapsed_time(start, end) / 1000
182+
print(f"{func_name}: {elapsed_time:.6f} s")
183+
184+
writer.writerow([func_name, dim, elapsed_time])
185+
186+
return result

0 commit comments

Comments
 (0)