I have boolean expression, which was simplified using Karnaugh's map (The first line). And then I used de Morgan's Law to make the expression suitable for using only NAND gates (The second line). But when I create a logic gate circuit it does not work properly and no matter how much I look at this circuit, I can't see where I made a mistake. And sorry for posting expression in a picture, I have no knowledge of how to transfer this expression from paper to computer.
I checked your circuit and have not been able to spot an error.
What is not working?
An alternative solution is:
NAND4(
NAND3(!X0, !X1, X3),
NAND4(X0, X1, X4, X5),
NAND4(!X0, X1, !X3, !X5),
NAND5(X0, !X1, !X2, X3, X4))
The solution generated by Logic Friday 1 is:
[][1]
Update:
I entered the following expression to Logic Friday 1:
INORDER = x5 x4 x3 x2 x1 x0;
F = !(!(!x0 & !(!(!x1 x3) & !(x1 !x3 !x5))) & !(x0 & !(!(x1 x4 x5) & !(!x1 !x2 !x3 x4))));
The resulting 18 minterms are:
Taking X5 as most-significant and X0 as least-significant bit, this can be interpreted as minterm list: 2, 6, 8, 12, 17, 18, 22, 24, 28, 40, 44, 49, 51, 55, 56, 59, 60, 63.
You can quickly convince yourself (minterm 63) that all six inputs set to 1 lead to output 1. Minterm 2: All inputs other than X1 0 leads to output 1 as well. Something might be different with your bit ordering.
Related
Im trying to evaluate this function in maple
but I keep getting this answer, why isn't maple integrating properly. I tried numerically integrating it and it works but I need the analytical solution too.
restart;
sig := x->(exp((x-t)/a)-exp((-x-t)/a))
/(exp((x-t)/a)+exp((-x-t)/a)):
new := convert(simplify(convert(expand(sig(x)),trigh)),tanh);
new := tanh(x/a)
simplify(expand(convert(sig(x) - new, exp)));
0
Now, you originally wrote int(f*sig(x)/x,x).
You didn't indicate that f was a function of x, and as a mere constant it's not really important and could simply be pulled out in front of the integral as a constant factor. If f is some function of x then you really need to state what it is!
Let's consider int(sig(x)/x,x=c..d). Using the simplification new, that is just,
Q := Int( new/x, x=c..d );
Q := Int(tanh(x/a)/x, x = c .. d)
QQ := IntegrationTools:-Change(Q, y=x/a, y);
QQ := Int(tanh(y)/y, y = c/a .. d/a)
You said that you wanted an "analytical solution" by which I take it you mean an explicit formula for the symbolic integration result. But what do you want if the integral does not (mathematically) have a closed form exact, symbolic result?
Would you be content with an (exact, symbolic) series approximation?
H := (a,ord,c,d)
-> int(convert(series(eval(new/x,:-a=a),x,ord),
polynom),x=c..d):
# order 5
H(a, 5, c, d);
3 3 / 5 5\
d - c -c + d 2 \-c + d /
----- - -------- + ------------
a 3 5
9 a 75 a
For a specific example, taking a=2 and an (exact) series approximation of order 25, then the integral from x=0 to x=1 gets evaluated as an exact rational.
evalf(H(2, 25, 0, 1));
0.4868885956
Here's the numeric integration for those same values,
evalf(Int( eval(new/x,a=2), x=0..1 ));
0.4868885956
Specialized numeric quadrature could be as good as a series approximation for a variety of applications, but of course that would depend on what you intend on doing with the result.
This raises the question: what do you hope to do with some supposed "analytical result" that you cannot do with a black-box function that generates the floating-point numeric approximation? Why do you "need" an "analytic result"?
BTW, another way to simplify it (in case the construction above of new does not succeed in your Maple version):
new := convert(simplify(expand( numer(sig(x))/exp(-t/a) ))
/simplify(expand( denom(sig(x))/exp(-t/a) )),
compose,trigh,tanh);
/x\
new := tanh|-|
\a/
I am translating a Matlab code into Fortran 90 and am trying to translate the following piece of code:
func= inline('x+ y+ z', 'x', 'y', 'z')
x(1)= 1, y(1)= 1, z(1)= 1
for n= 1:5
output= 5+ func(x(n), y(n), z(n))
x(n+ 1)= x(n)+ 1
y(n+ 1)= y(n)+ 1
z(n+ 1)= z(n)+ 1
end
In Fortran I am using the statement (inline) function as func(x, y, z)= x+ y+ z, however, I am not able to insert the array part into the function.
How can I negotiate the dependence on 'n' into the statement function? I am trying something like the following but am not quite there yet.
func(x, y, z)= x+ y+ z
x(1)= 1, y(1)= 1, z(1)= 1
do n= 1, 5
func(x(n), y(n), z(n))= x(n)+ y(n)+ z(n)
end
Any help would be greatly appreciated.
This is an extended and formatted comment rather than an answer.
The general advice with statement functions in modern Fortran is Don't, just don't. They're not big and they're not clever. They were also deprecated in, I think, the Fortran 90 standard so, to be pedantic, your requirements are inconsistent.
Beyond that, it's difficult to provide any specific advice. If I understand the Matlab correctly the code you show is a convoluted way to calculate 5+3*1+3*2+...+3*5. In Fortran 90 you might write
sum([5, (3*k,k=1,5)])
to calculate that.
Perhaps if we knew more of the context of your problem we'd be able to provide better advice.
I did realize that statement functions in modern Fortran is not the way to go. Instead I have created subroutines for the functions and then call them in the loop. This way all the values of the function in the loop can be put into an array (instead of just the last values). The correct piece of code looks like this:
subroutine funcsub(func, x, y, z, funcn)
implicit none
real, dimension(funcn), intent(out) :: func
real, dimension(funcn), intent(in) :: x, y, z
integer, intent(in) :: funky
func= x+ y+ z
end subroutine funcsub
do i= 1, 5
funcn= size(func)
call funcsub(func, x(i), y(i), z(i), funcn)
x(i+ 1)= x(i)+ 1
y(i+ 1)= y(i)+ 1
z(i+ 1)= z(i)+ 1
end do
I have a dataset comprising of 30 independent variables and I tried performing linear regression in MATLAB R2010b using the regress function.
I get a warning stating that my matrix X is rank deficient to within machine precision.
Now, the coefficients I get after executing this function don't match with the experimental one.
Can anyone please suggest me how to perform the regression analysis for this equation which is comprising of 30 variables?
Going with our discussion, the reason why you are getting that warning is because you have what is known as an underdetermined system. Basically, you have a set of constraints where you have more variables that you want to solve for than the data that is available. One example of an underdetermined system is something like:
x + y + z = 1
x + y + 2z = 3
There are an infinite number of combinations of (x,y,z) that can solve the above system. For example, (x, y, z) = (1, −2, 2), (2, −3, 2), and (3, −4, 2). What rank deficient means in your case is that there is more than one set of regression coefficients that would satisfy the governing equation that would describe the relationship between your input variables and output observations. This is probably why the output of regress isn't matching up with your ground truth regression coefficients. Though it isn't the same answer, do know that the output is one possible answer. By running through regress with your data, this is what I get if I define your observation matrix to be X and your output vector to be Y:
>> format long g;
>> B = regress(Y, X);
>> B
B =
0
0
28321.7264417536
0
35241.9719076362
899.386999172398
-95491.6154990829
-2879.96318251964
-31375.7038251919
5993.52959752106
0
18312.6649115112
0
0
8031.4391233753
27923.2569044728
7716.51932560781
-13621.1638587172
36721.8387047613
80622.0849069525
-114048.707780113
-70838.6034825939
-22843.7931997405
5345.06937207617
0
106542.307940305
-14178.0346010715
-20506.8096166108
-2498.51437396558
6783.3107243113
You can see that there are seven regression coefficients that are equal to 0, which corresponds to 30 - 23 = 7. We have 30 variables and 23 constraints to work with. Be advised that this is not the only possible solution. regress essentially computes the least squared error solution such that sum of residuals of Y - X*B has the least amount of error. This essentially simplifies to:
B = X^(*)*Y
X^(*) is what is known as the pseudo-inverse of the matrix. MATLAB has this available, and it is called pinv. Therefore, if we did:
B = pinv(X)*Y
We get:
B =
44741.6923363563
32972.479220139
-31055.2846404536
-22897.9685877566
28888.7558524005
1146.70695371731
-4002.86163441217
9161.6908044046
-22704.9986509788
5526.10730457192
9161.69080479427
2607.08283489226
2591.21062004404
-31631.9969765197
-5357.85253691504
6025.47661106009
5519.89341411127
-7356.00479046122
-15411.5144034056
49827.6984426955
-26352.0537850382
-11144.2988973666
-14835.9087945295
-121.889618144655
-32355.2405829636
53712.1245333841
-1941.40823106236
-10929.3953469692
-3817.40117809984
2732.64066796307
You see that there are no zero coefficients because pinv finds the solution using the L2-norm, which promotes the "spreading" out of the errors (for a lack of a better term). You can verify that these are correct regression coefficients by doing:
>> Y2 = X*B
Y2 =
16.1491563400241
16.1264219600856
16.525331600049
17.3170318001845
16.7481541301999
17.3266932502295
16.5465094100486
16.5184456100487
16.8428701100165
17.0749421099829
16.7393450000517
17.2993993099419
17.3925811702017
17.3347117202356
17.3362798302375
17.3184486799219
17.1169638102517
17.2813552099096
16.8792925100727
17.2557945601102
17.501873690151
17.6490477001922
17.7733493802508
Similarly, if we used the regression coefficients from regress, so B = regress(Y,X); then doing Y2 = X*B, we get:
Y2 =
16.1491563399927
16.1264219599996
16.5253315999987
17.3170317999969
16.7481541299967
17.3266932499992
16.5465094099978
16.5184456099983
16.8428701099975
17.0749421099985
16.7393449999981
17.2993993099983
17.3925811699993
17.3347117199991
17.3362798299967
17.3184486799987
17.1169638100025
17.281355209999
16.8792925099983
17.2557945599979
17.5018736899983
17.6490476999977
17.7733493799981
There are some slight computational differences, which is to be expected. Similarly, we can also find the answer by using mldivide:
B = X \ Y
B =
0
0
28321.726441712
0
35241.9719075889
899.386999170666
-95491.6154989513
-2879.96318251572
-31375.7038251485
5993.52959751295
0
18312.6649114859
0
0
8031.43912336425
27923.2569044349
7716.51932559712
-13621.1638586983
36721.8387047123
80622.0849068411
-114048.707779954
-70838.6034824987
-22843.7931997086
5345.06937206919
0
106542.307940158
-14178.0346010521
-20506.8096165825
-2498.51437396236
6783.31072430201
You can see that this curiously matches up with what regress gives you. That's because \ is a more smarter operator. Depending on how your matrix is structured, it finds the solution to the system by a different method. I'd like to defer you to the post by Amro that talks about what algorithms mldivide uses when examining the properties of the input matrix being operated on:
How to implement Matlab's mldivide (a.k.a. the backslash operator "\")
What you should take away from this answer is that you can certainly go ahead and use those regression coefficients and they will more or less give you the expected output for each value of Y with each set of inputs for X. However, be warned that those coefficients are not unique. This is apparent as you said that you have ground truth coefficients that don't match up with the output of regress. It isn't matching up because it generated another answer that satisfies the constraints you have provided.
There is more than one answer that can describe that relationship if you have an underdetermined system, as you have seen by my experiments shown above.
I'm working on some Matlab code to perform something called the Index Calculus attack on a given cryptosystem (this involves calculating discrete log values), and I've gotten it all done except for one small thing. I cant figure out (in Matlab) how to solve a linear system of congruences mod p, where p is not prime. Also, this system has more than one variable, so, unless I'm missing something, the Chinese remainder theorem wont work.
I asked a question on the mathematics stackexchange with more detail/formatted mathjax here. I solved the issue in my question at that link, and now I'm attempting to find a utility that will allow me to solve the system of congruences modulo a non-prime. I did find a suite that includes a solver supporting modular arithmetic, but the modulus must be prime (here). I also tried stepping through to modify it to work with non-primes, but whatever method is used doesn't work, because it requires all elements of the system have inverses modulo p.
I've looked into using the ability in Matlab to call MuPAD functions, but from my testing, the MuPAD function linsolve (which seemed to be the best candidate) doesn't support non-prime modulus values either. Additionally, I've verified with Maple that this system is solvable modulo my integer of interest (8), so it can be done.
To be more specific, this is the exact command I'm trying to run in MuPAD:
linsolve([0*x + 5*y + 4*z + q = 2946321, x + 7*y + 2*q = 5851213, 8*x + y + 2*q = 2563617, 10*x + 5*y + z = 10670279],[x,y,z,q], Domain = Dom::IntegerMod(8))
Error: expecting 'Domain=R', where R is a domain of category 'Cat::Field' [linsolve]
The same command returns correct values if I change the domain to IntegerMod(23) and IntegerMod(59407), so I believe 8 is unsuitable because it's not prime. Here is the output when I try the above command with each 23 and 59407 as my domain:
[x = 1 mod 23, y = 1 mod 23, z = 12 mod 23, q = 14 mod 23]
[x = 14087 mod 59407, y = 1 mod 59407, z = 14365 mod 59407, q = 37320 mod 59407]
These answers are correct- x, y, z, and q correspond to L1, L2, L3, and L4 in the system of congruences located at my Math.StackExchange link above.
I'm wondering if you tried to use sym/linsolve and sym/solve previously, but may have passed in numeric rather than symbolic values. For example, this returns nonsense in terms of what you're looking for:
A = [0 5 4 1;1 7 0 2;8 1 0 2;10 5 1 0];
b = [2946321;5851213;2563617;10670279];
s = mod(linsolve(A,b),8)
But if you convert the numeric values to symbolic integers, sym/linsolve will keep everything in terms of rational fractions. Then
s = mod(linsolve(sym(A),sym(b)),8)
returns the expected answer
s =
6
1
6
4
This just solves the system linear system using symbolic math as if it were a normal matrix. For large systems this can be expensive, but I'd imagine no more than using MuPAD's numeric::linsolve or linalg::matlinsolve. sym/mod should return the modulus of the numerator of each solution component. I believe that you will get an error if the modulus and the denominator are not at least coprime.
sym/solve can also be used to solve this in a similar manner:
L = sym('L',[4,1]);
[L1,L2,L3,L4] = solve(A*L==b);
s = mod([L1;L2;L3;L4],8)
A possible issue with using either sym/solve or sym/linsolve is that if there are multiple solutions to the linear congruence problem (as opposed to the linear system), this approach may not return all of them.
Finally, using the MuPAD function numlib::ichrem (chinese remainder theorem for integers), here's some code that attempts to obtain the complete solution:
A = [0 5 4 1;1 7 0 2;8 1 0 2;10 5 1 0];
b = [2946321;5851213;2563617;10670279];
m = 10930888;
mf = str2num(strrep(char(factor(sym(m))),'*',' '));
A = sym(A);
b = sym(b);
s = sym(zeros(length(b),length(mf)));
for i = 1:length(mf)
s(:,i) = mod(linsolve(A,b),mf(i));
end
mstr = ['[' sprintf('%d,',mf)];
mstr(end) = ']';
r = sym(zeros(length(b),1));
for i = 1:length(b)
sstr = char(s(i,:));
r(i) = feval(symengine,'numlib::ichrem',sstr(9:end-2),mstr);
end
check = isequal(mod(A*r,m),b)
I'm not sure if any of this is what you're looking for, but hopefully it might be helpful. I think that it might be a good idea to put in a enhancement/service request with the MathWorks so that MuPAD and the other solvers can handle systems better in the future.
I have a fairly complex optimization problem set up that I've solved through fmincon by calling it like this
myfun = #(x5) 0.5 * (norm(C*x5 - d))^2 + 0.5 * (timeIntervalMeanGlobal * powerAbsMaxMaxGlobal * sum(x5(28:128),1))^2;
[x5, fval] = fmincon(myfun, initialGuess, -A, b, Aeq, beq, lb, []);
The components are far to long to print here, but here are the dimensions
C: 49 x 128
x5: 128 x 1
d: 49 x 1
timeIntervalMeanGlobal, powerAbsMaxMaxGlobal: constants
initialGuess: 128 x 1
A: 44541 x 128
b: 44541 x 1
Aeq: 24 x 128
beq: 24 x 1
lb: 128 x 1
This works in code, but I don't get results that I'm completely happy with. I'd like to compare it with the built in ga function in MATLAB, which is called in a similar way, but I get an error when I try to run it like this
[x5, fval] = ga(myfun, nvars, -A, b, Aeq, beq, lb, []);
where nvars = 128. There's a long list of about 8 errors starting with
??? Error using ==> mtimes
Inner matrix dimensions must agree.
and ending with
Caused by:
Failure in user-supplied fitness function evaluation. GA cannot continue.
Can someone please instruct me on how to call ga properly, and give insight on why this error might occur with the ga call when the same code doesn't cause an error with fmincon? I've tried all the MATLAB help files and examples with a few different permutations of this but no better luck. Thanks.
UPDATE: I think I found the problem but I don't know how to fix it. The ga documentation says "The fitness function should accept a row vector of length nvars". In my case, myfun is the fitness function, but x5 is a column vector (so is lb). So while mathematically I know that C*x5 = d is the same as x5'*C' = d' even for non-square matrices, I can't formulate the problem that way for the ga solver. I tried - it makes it past the fitness function but then I get the error
The number of rows in A must be the same as the length of b.
Any thoughts on how to get this problem in the right format for the solver? Thanks!
Got it! I just had to manipulate the fitness function to make it use x5 as a row vector even though it's a column vector in all the constraints
myfun = #(x5) 0.5 * (norm(x5 * C' - d'))^2 + 0.5 * (timeIntervalMeanGlobal * powerAbsMaxMaxGlobal * sum(x5(28:128)))^2;
Phew!