#include<bits/stdc++.h>
using namespace std;
long long int f(int a){
if(a==0 || a==1) return a;
return f(a-1) + f(a-2);
}
int main(){
struct timespec start, end;
clock_gettime(CLOCK_MONOTONIC, &start);
for(int i=0;i<50;i++){
cout<<f(i)<<endl;
}
clock_gettime(CLOCK_MONOTONIC, &end);
long long int secs = end.tv_sec - start.tv_sec;
long long int nsecs = end.tv_nsec - start.tv_nsec;
double elapsed = secs + nsecs * 1e-9;
cout << "Time spent: " << elapsed << " secs" << endl;
return 0;
}
Output
kishan@kishan-IdeaPad-3-15IIL05:~/Desktop/CompArc$ g++ -o a Q1a.cpp
kishan@kishan-IdeaPad-3-15IIL05:~/Desktop/CompArc$ ./a
0
1
1
2
3
5
8
13
21
34
55
89
144
233
377
610
987
1597
2584
4181
6765
10946
17711
28657
46368
75025
121393
196418
317811
514229
832040
1346269
2178309
3524578
5702887
9227465
14930352
24157817
39088169
63245986
102334155
165580141
267914296
433494437
701408733
1134903170
1836311903
2971215073
4807526976
7778742049
Time spent: 410.978 seconds
Execution | Time Spent (seconds) |
---|---|
First | 410.978 s |
Second | 412.223 s |
Third | 417.328 s |
Average time = (410.978 + 417.223 + 417.328)/3 = 415.176333333 s
Median execution time = 412.233 s
#include<bits/stdc++.h>
using namespace std;
int main(){
struct timespec start, end;
clock_gettime(CLOCK_MONOTONIC, &start);
for(int i=0;i<50;i++){
long long int x=0,y=1;
if(i==0) cout<<x<<endl;
else if(i==1) cout<<y<<endl;
else{
for(int j=2;j<=i;j++){
long long int t = x+y;
x=y;
y=t;
}
}
cout<<y<<endl;
}
clock_gettime(CLOCK_MONOTONIC, &end);
long long int secs = end.tv_sec - start.tv_sec;
long long int nsecs = end.tv_nsec - start.tv_nsec;
double elapsed = secs + nsecs * 1e-9;
cout << "Time spent: " << elapsed << " secs" << endl;
return 0;
}
Output
kishan@kishan-IdeaPad-3-15IIL05:~/Desktop/CompArc$ ./a
0
1
1
1
1
2
3
5
8
13
21
34
55
89
144
233
377
610
987
1597
2584
4181
6765
10946
17711
28657
46368
75025
121393
196418
317811
514229
832040
1346269
2178309
3524578
5702887
9227465
14930352
24157817
39088169
63245986
102334155
165580141
267914296
433494437
701408733
1134903170
1836311903
2971215073
4807526976
7778742049
Time spent: 0.000242781 secs
Execution | Time Spent (seconds) |
---|---|
First | 0.000242781 s |
Second | 0.000265847 s |
Third | 0.000242290 s |
Average time = (0.000242781 + 0.000265847 + 0.00024229)/3 = 0.000250306 s
Median time = 0.000242781 s
#include<bits/stdc++.h>
using namespace std;
long long int f(int a, vector<long long int>& v){
if(a==0 || a==1) return a;
if(v[a]!=-1) return v[a];
return v[a] = f(a-1,v) + f(a-2,v);
}
int main(){
struct timespec start, end;
clock_gettime(CLOCK_MONOTONIC, &start);
vector<long long int> v(50,-1);
for(int i=0;i<50;i++){
cout<<f(i,v)<<endl;
}
clock_gettime(CLOCK_MONOTONIC, &end);
long long int secs = end.tv_sec - start.tv_sec;
long long int nsecs = end.tv_nsec - start.tv_nsec;
double elapsed = secs + nsecs * 1e-9;
cout << "Time spent: " << elapsed << " secs" << endl;
return 0;
}
Output
kishan@kishan-IdeaPad-3-15IIL05:~/Desktop/CompArc$ g++ -o a Q1c.cpp
kishan@kishan-IdeaPad-3-15IIL05:~/Desktop/CompArc$ ./a
0
1
1
2
3
5
8
13
21
34
55
89
144
233
377
610
987
1597
2584
4181
6765
10946
17711
28657
46368
75025
121393
196418
317811
514229
832040
1346269
2178309
3524578
5702887
9227465
14930352
24157817
39088169
63245986
102334155
165580141
267914296
433494437
701408733
1134903170
1836311903
2971215073
4807526976
7778742049
Time spent: 0.000230712 secs
Execution | Time Spent (seconds) |
---|---|
First | 0.000230712 s |
Second | 0.000228272 s |
Third | 0.000235082 s |
Average time = (0.000230712 + 0.000228272 + 0.000235082)/3 = 0.00023135533 s
Median time = 0.000230712 s
#include<bits/stdc++.h>
using namespace std;
int main(){
struct timespec start, end;
clock_gettime(CLOCK_MONOTONIC, &start);
vector<long long int> v(50);
v[0] = 0;
v[1] = 1;
for(int i=0;i<50;i++){
v[i] = v[i-1]+v[i-2];
cout<<v[i]<<endl;
}
clock_gettime(CLOCK_MONOTONIC, &end);
long long int secs = end.tv_sec - start.tv_sec;
long long int nsecs = end.tv_nsec - start.tv_nsec;
double elapsed = secs + nsecs * 1e-9;
cout << "Time spent: " << elapsed << " secs" << endl;
return 0;
}
Output
kishan@kishan-IdeaPad-3-15IIL05:~/Desktop/CompArc$ g++ -o a Q1c.cpp
kishan@kishan-IdeaPad-3-15IIL05:~/Desktop/CompArc$ ./a
0
1
1
2
3
5
8
13
21
34
55
89
144
233
377
610
987
1597
2584
4181
6765
10946
17711
28657
46368
75025
121393
196418
317811
514229
832040
1346269
2178309
3524578
5702887
9227465
14930352
24157817
39088169
63245986
102334155
165580141
267914296
433494437
701408733
1134903170
1836311903
2971215073
4807526976
7778742049
Time spent: 0.000152432 secs
Execution | Time Spent (seconds) |
---|---|
First | 0.000152432 s |
Second | 0.000189024 s |
Third | 0.000164013 s |
Average time = (0.000152432 + 0.000189024 + 0.000164013)/3 = 0.00016848966 s
Median time = 0.000164013 s
- (d) Loop with memoization (0.000164013 s)
- (c) Recursion with memoization (0.000230712 s)
- (b) Loop (0.000242781 s)
- (a) Recursion (412.233 s)
Speedup of (b) wrt (a) = Average time of (a) / Average time of (b) = 415.176333333 / 0.000250306 = 1658675.11499
Speedup of (c) wrt (a) = Average time of (a) / Average time of (b) = 415.176333333 / 0.00023135533 = 1794539.73822
Speedup of (d) wrt (a) = Average time of (a) / Average time of (b) = 415.176333333 / 0.00016848966 = 2464105.7103
- (a) runs in exponential time
- (b) runs in O(N2) time
- (c) runs in O(N) time (but involves recursion, which is slower than iteration)
- (d) runs in O(N) time and is iterative
For this part, I have shown 3 outputs, and then performed the average of these to get the final times.
The code remains the same for all, the only difference is in the value assigned to variable n
#include<bits/stdc++.h>
using namespace std;
using namespace chrono;
int main() {
int N = 1024;
vector<vector<int>> A(N, vector<int>(N));
vector<vector<int>> B(N, vector<int>(N));
vector<vector<int>> C(N, vector<int>(N, 0));
for (int i = 0; i < N; ++i) {
for (int j = 0; j < N; ++j) {
A[i][j] = rand() % 100;
B[i][j] = rand() % 100;
}
}
struct timespec start, end;
clock_gettime(CLOCK_MONOTONIC, &start);
for (int i = 0; i < N; ++i) {
for (int j = 0; j < N; ++j) {
for (int k = 0; k < N; ++k) {
C[i][j] += A[i][k] * B[k][j];
}
}
}
clock_gettime(CLOCK_MONOTONIC, &end);
long long int secs = end.tv_sec - start.tv_sec;
long long int nsecs = end.tv_nsec - start.tv_nsec;
double elapsed = secs + nsecs * 1e-9;
cout << "Time spent: " << elapsed << " secs" << endl;
return 0;
}
Output 1 (done using the terminal command: time ./a):
kishan@kishan-IdeaPad-3-15IIL05:~/Desktop/CompArc$ time ./a
Time spent: 0.00616353 secs
real 0m0.013s
user 0m0.008s
sys 0m0.005s
Output 2:
kishan@kishan-IdeaPad-3-15IIL05:~/Desktop/CompArc$ time ./a
Time spent: 0.00602613 secs
real 0m0.012s
user 0m0.008s
sys 0m0.005s
Output 3:
kishan@kishan-IdeaPad-3-15IIL05:~/Desktop/CompArc$ time ./a
Time spent: 0.00682563 secs
real 0m0.014s
user 0m0.010s
sys 0m0.004s
Execution | Time Spent (seconds) | Real Time | User Time | Sys Time |
---|---|---|---|---|
First | 0.00616353 | 0m0.013s | 0m0.008s | 0m0.005s |
Second | 0.00602613 | 0m0.012s | 0m0.008s | 0m0.005s |
Third | 0.00682563 | 0m0.014s | 0m0.010s | 0m0.004s |
- Time spent on matrix multiplication: 0.00616353 secs
- Real CPU time: 0.013 s
- User CPU time : 0.008 s
- Sys CPU time: 0.005 s
Proportion of meat portion wrt actual program: (0.00616353/0.013) = 0.47412
Execution | Meat portion (seconds) | Real Time | User Time | Sys Time |
---|---|---|---|---|
First | 0.0494252 | 0m0.057s | 0m0.052s | 0m0.005s |
Second | 0.0595929 | 0m0.068s | 0m0.067s | 0m0.002s |
Third | 0.0487691 | 0m0.056s | 0m0.050s | 0m0.006s |
- Time spent: 0.0494252 secs
- real CPU time: 0.057s
- user CPU time: 0.052s
- sys CPU time: 0.005s
Proportion of meat portion wrt actual program: (0.0494252/0.057) = 0.86711
Execution | Time Spent (seconds) | Real Time | User Time | Sys Time |
---|---|---|---|---|
First | 0.358945 | 0m0.373s | 0m0.371s | 0m0.002s |
Second | 0.361204 | 0m0.375s | 0m0.368s | 0m0.006s |
Third | 0.362392 | 0m0.376s | 0m0.370s | 0m0.005s |
- Median Time Spent: 0.361204 seconds
- Median Real Time: 0m0.375s
- Median User Time: 0m0.370s
- Median Sys Time: 0m0.005s
Proportion of meat portion wrt actual program: (0.361204/0.375) = 0.96321
Execution | Time Spent (seconds) | Real Time | User Time | Sys Time |
---|---|---|---|---|
First | 3.24841 | 0m3.284s | 0m3.277s | 0m0.006s |
Second | 3.14960 | 0m3.185s | 0m3.116s | 0m0.008s |
Third | 3.20658 | 0m3.244s | 0m3.236s | 0m0.009s |
- Median Time Spent: 3.20658 seconds
- Median Real Time: 0m3.244s
- Median User Time: 0m3.236s
- Median Sys Time: 0m0.008s
Proportion of meat portion wrt actual program: (3.20658/3.244) = 0.98846
Execution | Time Spent (seconds) | Real Time | User Time | Sys Time |
---|---|---|---|---|
First | 24.2351 | 0m24.354s | 0m24.315s | 0m0.025s |
Second | 27.8404 | 0m27.961s | 0m27.933s | 0m0.015s |
Third | 29.0739 | 0m29.198s | 0m29.140s | 0m0.053s |
- Median Time Spent: 27.8404 seconds
- Median Real Time: 0m27.961s
- Median User Time: 0m27.933s
- Median Sys Time: 0m0.025s
Proportion of meat portion wrt actual program: (27.8404/27.961) = 0.99569
import numpy as np
import time
N = 64
matA = np.random.randint(0, 100, (N, N))
matB = np.random.randint(0, 100, (N, N))
matC = np.zeros((N, N), dtype=int)
start = time.time()
for i in range(N):
for j in range(N):
for k in range(N):
matC[i][j] += matA[i][k] * matB[k][j]
end = time.time()
elapsed = end - start
print(f"Time spent: {elapsed} secs")
In this part, I have performed 3 iterations and taken the median (as done above), and only the median value is mentioned below.
- Time spent: 0.5385956764221191 secs
- real 0m1.001s
- user 0m1.100s
- sys 0m1.155s
Proportion of meat portion wrt actual program: (0.5386/1.0010) = 0.538
- Time spent: 3.481839179992676 secs
- real 0m3.843s
- user 0m4.049s
- sys 0m1.052s
Proportion of meat portion wrt actual program: (3.4818/3.8430) = 0.906
- Time spent: 26.963408946990967 secs
- real 0m27.257s
- user 0m27.576s
- sys 0m1.206s
Proportion of meat portion wrt actual program: (26.9634/27.2570) = 0.989
- Time spent: 228.12692141532898 secs
- real 3m48.455s
- user 3m48.729s
- sys 0m1.206s
Proportion of meat portion wrt actual program: (228.1269/228.4550) = 0.99902
- Time spent: 1846.78790787841567 secs
- real 30m48.322s
- user 30m57.344s
- sys 0m1.291s
Proportion of meat portion wrt actual program: (1846.7879/1848.322) = 0.99917
In this part, I have performed 3 iterations and taken the median (as done above), and only the median value is mentioned below.
#include <bits/stdc++.h>
using namespace std;
using namespace chrono;
int main() {
int N = 64;
vector<vector<double>> matA(N, vector<float>(N));
vector<vector<double>> matB(N, vector<float>(N));
vector<vector<double>> matC(N, vector<float>(N, 0.0f));
for (int i = 0; i < N; ++i) {
for (int j = 0; j < N; ++j) {
matA[i][j] = static_cast<float>(rand()) / RAND_MAX * 100.0f;
matB[i][j] = static_cast<float>(rand()) / RAND_MAX * 100.0f;
}
}
struct timespec start, end;
clock_gettime(CLOCK_MONOTONIC, &start);
for (int i = 0; i < N; ++i) {
for (int j = 0; j < N; ++j) {
for (int k = 0; k < N; ++k) {
matC[i][j] += matA[i][k] * matB[k][j];
}
}
}
clock_gettime(CLOCK_MONOTONIC, &end);
long long int secs = end.tv_sec - start.tv_sec;
long long int nsecs = end.tv_nsec - start.tv_nsec;
double elapsed = secs + nsecs * 1e-9;
cout << "Time spent: " << elapsed << " secs" << endl;
return 0;
}
- Time spent: 0.0118847 secs
- real 0m0.018s
- user 0m0.018s
- sys 0m0.001s
Proportion of meat portion wrt actual program: (0.01188/0.018) = 0.66
- Time spent: 0.0641931 secs
- real 0m0.072s
- user 0m0.068s
- sys 0m0.002s
Proportion of meat portion wrt actual program: (0.06419/0.072) = 0.8915
- Time spent: 0.364272 secs
- real 0m0.379s
- user 0m0.375s
- sys 0m0.004s
Proportion of meat portion wrt actual program: (0.3643/0.379) = 0.9612
- Time spent: 3.11515 secs
- real 0m3.156s
- user 0m3.154s
- sys 0m0.001s
Proportion of meat portion wrt actual program: (3.1152/3.156) = 0.98707
- Time spent: 26.5513 secs
- real 0m26.669s
- user 0m26.659s
- sys 0m0.007s
Proportion of meat portion wrt actual program: (26.5513/26.669) = 0.99559
import numpy as np
import time
N = 1024
matA = np.random.uniform(0, 100, (N, N))
matB = np.random.uniform(0, 100, (N, N))
matC = np.zeros((N, N), dtype=float)
start = time.time()
for i in range(N):
for j in range(N):
for k in range(N):
matC[i][j] += matA[i][k] * matB[k][j]
end = time.time()
elapsed = end - start
print(f"Time spent: {elapsed} secs")
In this part, I have performed 3 iterations and taken the median (as done above), and only the median value is mentioned below.
- Time spent: 0.45248913764953613 secs
- real 0m0.742s
- user 0m1.066s
- sys 0m1.232s
Proportion of meat portion wrt actual program: (0.4525/0.7420) = 0.61
- Time spent: 4.212065935134888 secs
- real 0m4.510s
- user 0m4.806s
- sys 0m1.256s
Proportion of meat portion wrt actual program: (4.2121/4.5100) = 0.934
- Time spent: 28.8769314289093 secs
- real 0m29.182s
- user 0m29.399s
- sys 0m1.309s
Proportion of meat portion wrt actual program: (28.8769/29.1820) = 0.9895
- Time spent: 230.83469247817993 secs
- real 3m51.144s
- user 3m51.395s
- sys 0m1.266s
Proportion of meat portion wrt actual program: (230.8347/231.1440) = 0.9986
- Time spent: 1855.48235671256894 secs
- real 30m59.855s
- user 31m0.099s
- sys 0m1.301s
Proportion of meat portion wrt actual program: (1855.4824/1859.855) = 0.9996
- System CPU time is much lower than User CPU time
- The System CPU time is nearly constant (or increases very slightly on increasing the value of N), this is because it is the amount of time the CPU was busy executing code in kernel space. This does not include the meat portion of the program.
- The time taken for the meat portion of the program is included in the user CPU time
- The time taken for executing C++ code is much lesser than the time taken by the Python code
- The real CPU time is almost equal to the user CPU time, as the system CPU time is very low
- As the value of N increases, the time taken increases. Roughly, when N is doubled, the total CPU time becomes 8 times. This is because matrix multiplication is an O(N^3) operation, and 2^3 = 8
- As the value of N increases, the proportion of meat protion's time wrt actual program's time becomes closer to 1, this is because the system time is nearly constant and the user CPU time increases (as the number of operations to be performed increase) on increasing the value of N.
- The number of operations perfomed in a unit time is larger for C++ when compared to Python. This is because of the language design
- For both Python and C++, the integer operations are faster (based on total CPU time), this is becuase they require lesser memory (int datatype in C++ is 4 bytes while double is 8 bytes), moreover, integer operations are simpler, they involve basic circuitry (if translated to circuit based operations), double datatype on the other hand requires more complex handling of the decimal and the fractional part (which increases the number of operations needed, as they have more precision when compared to int). Converting int from decimal to binary is also simpler (requires lesser operations) than converting a double value to binary