Add some polynomial vector and number classs
This commit is contained in:
593
src/awt/Draw.java
Normal file
593
src/awt/Draw.java
Normal file
@@ -0,0 +1,593 @@
|
|||||||
|
package awt;
|
||||||
|
|
||||||
|
import javax.swing.JLabel;
|
||||||
|
import javax.swing.SwingConstants;
|
||||||
|
import javax.swing.SwingUtilities;
|
||||||
|
|
||||||
|
import math.Maths;
|
||||||
|
import math.matrix.Matrix;
|
||||||
|
import math.matrix.Vector;
|
||||||
|
import physics.Nyquist;
|
||||||
|
import stdlib.Color;
|
||||||
|
import stdlib.StdDraw;
|
||||||
|
|
||||||
|
public class Draw extends StdDraw{
|
||||||
|
static Thread plot;
|
||||||
|
static JLabel infoLabel;
|
||||||
|
|
||||||
|
public static double scaleLeft = -10;
|
||||||
|
public static double scaleRight = 10;
|
||||||
|
public static double scaleBottom = -10;
|
||||||
|
public static double scaleTop = 10;
|
||||||
|
|
||||||
|
// TODO: combine X,Y,XM,YM ???
|
||||||
|
// see in animate
|
||||||
|
static double[] X;
|
||||||
|
static double[] Y;
|
||||||
|
static Matrix XM;
|
||||||
|
static Matrix YM;
|
||||||
|
|
||||||
|
static Matrix M;
|
||||||
|
static Matrix dM;
|
||||||
|
static Vector m; // for FEM
|
||||||
|
static double fac; // for FEM
|
||||||
|
|
||||||
|
boolean animationSet = false;
|
||||||
|
|
||||||
|
private static double process;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* plot
|
||||||
|
*/
|
||||||
|
public Draw(){
|
||||||
|
setupGUI();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* plot
|
||||||
|
*/
|
||||||
|
public Draw(String title){
|
||||||
|
setupGUI(title);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* xy-plot
|
||||||
|
* @param X
|
||||||
|
* @param Y
|
||||||
|
*/
|
||||||
|
public Draw(int[] X, int[] Y){
|
||||||
|
setupGUI();
|
||||||
|
allocation(X, Y);
|
||||||
|
setScale(Maths.min(X)*1.1, Maths.max(X)*1.1, Maths.min(Y)*1.1, Maths.max(Y)*1.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* xy-plot
|
||||||
|
* @param X
|
||||||
|
* @param Y
|
||||||
|
*/
|
||||||
|
public Draw(int[] X, int[] Y, String title){
|
||||||
|
setupGUI(title);
|
||||||
|
allocation(X, Y);
|
||||||
|
setScale(Maths.min(X)*1.1, Maths.max(X)*1.1, Maths.min(Y)*1.1, Maths.max(Y)*1.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* xy-plot
|
||||||
|
* @param X
|
||||||
|
* @param Y
|
||||||
|
*/
|
||||||
|
public Draw(double[] X, double[] Y){
|
||||||
|
setupGUI();
|
||||||
|
allocation(X, Y);
|
||||||
|
setScale(Maths.min(X)*1.1, Maths.max(X)*1.1, Maths.min(Y)*1.1, Maths.max(Y)*1.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* xy-plot
|
||||||
|
* @param X
|
||||||
|
* @param Y
|
||||||
|
*/
|
||||||
|
public Draw(double[] X, double[] Y, String title){
|
||||||
|
setupGUI(title);
|
||||||
|
allocation(X, Y);
|
||||||
|
setScale(Maths.min(X)*1.1, Maths.max(X)*1.1, Maths.min(Y)*1.1, Maths.max(Y)*1.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* xy-plot
|
||||||
|
* @param X
|
||||||
|
* @param Y
|
||||||
|
*/
|
||||||
|
public Draw(Vector X, Vector Y){
|
||||||
|
setupGUI();
|
||||||
|
allocation(X, Y);
|
||||||
|
setScale(X.min()*1.1, X.max()*1.1, Y.min()*1.1, Y.max()*1.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* xy-plot
|
||||||
|
* @param X
|
||||||
|
* @param Y
|
||||||
|
*/
|
||||||
|
public Draw(Vector X, Vector Y, String title){
|
||||||
|
setupGUI(title);
|
||||||
|
allocation(X, Y);
|
||||||
|
setScale(X.min()*1.1, X.max()*1.1, Y.min()*1.1, Y.max()*1.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* xy-plot
|
||||||
|
* @param X
|
||||||
|
* @param Y
|
||||||
|
*/
|
||||||
|
public Draw(Matrix X, Matrix Y){
|
||||||
|
setupGUI();
|
||||||
|
allocation(X, Y);
|
||||||
|
setScale(X.min()*1.1, X.max()*1.1, Y.min()*1.1, Y.max()*1.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* xy-plot
|
||||||
|
* @param X
|
||||||
|
* @param Y
|
||||||
|
*/
|
||||||
|
public Draw(Matrix X, Matrix Y, String title){
|
||||||
|
setupGUI(title);
|
||||||
|
allocation(X, Y);
|
||||||
|
setScale(X.min()*1.1, X.max()*1.1, Y.min()*1.1, Y.max()*1.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// GUI
|
||||||
|
|
||||||
|
private void setupGUI(){
|
||||||
|
frame.setLocation(100, 50);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void setupGUI(String title){
|
||||||
|
frame.setLocation(100, 50);
|
||||||
|
frame.setTitle(title);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setBGC(Color bgColor){
|
||||||
|
clear(bgColor);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setFGC(Color Color){
|
||||||
|
setGraphColor(Color);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Graph
|
||||||
|
|
||||||
|
private void allocation(int[] X, int[] Y){
|
||||||
|
int imax = X.length;
|
||||||
|
Draw.XM = new Matrix(imax,1);
|
||||||
|
Draw.YM = new Matrix(imax,1);
|
||||||
|
int i;
|
||||||
|
for(i=0; i<imax; i++){
|
||||||
|
Draw.XM.set(i, 1, X[i]);
|
||||||
|
Draw.YM.set(i, 1, Y[i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void allocation(double[] X, double[] Y){
|
||||||
|
Draw.XM = new Matrix(X).transpose(); // datas in rows
|
||||||
|
Draw.YM = new Matrix(Y).transpose();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void allocation(Vector X, Vector Y){
|
||||||
|
Draw.XM = new Matrix(X).transpose(); // datas in rows
|
||||||
|
Draw.YM = new Matrix(Y).transpose();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void allocation(Matrix X, Matrix Y){
|
||||||
|
Draw.XM = X;
|
||||||
|
Draw.YM = Y;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setScale(double x1, double x2, double y1, double y2){
|
||||||
|
scaleLeft = x1;
|
||||||
|
scaleRight = x2;
|
||||||
|
scaleBottom = y1;
|
||||||
|
scaleTop = y2;
|
||||||
|
|
||||||
|
setXscale(scaleLeft, scaleRight);
|
||||||
|
setYscale(scaleBottom, scaleTop);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static double getProcess() {
|
||||||
|
return process;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void setProcess(double process) {
|
||||||
|
Draw.process = process;
|
||||||
|
infoLabel.setText(String.format("%.0f %%",process));
|
||||||
|
}
|
||||||
|
|
||||||
|
public void plot(){
|
||||||
|
contents();
|
||||||
|
int i;
|
||||||
|
double x = 0.0, y = 0.0;
|
||||||
|
if(X!=null){
|
||||||
|
setPenColor(Color.LIGHT_GRAY); // BLUE
|
||||||
|
int imax = X.length;
|
||||||
|
for(i=0; i<imax; i++){
|
||||||
|
x = X[i];
|
||||||
|
y = Y[i];
|
||||||
|
point(x, y);
|
||||||
|
// System.out.println(y);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void plotLines(double[][] A, double[][] dA){
|
||||||
|
M = new Matrix(A);
|
||||||
|
dM = new Matrix(dA);
|
||||||
|
contents();
|
||||||
|
if(M!=null){
|
||||||
|
int i;
|
||||||
|
int imax = M.getM();
|
||||||
|
double f = 50;
|
||||||
|
// System.out.println(f);
|
||||||
|
clear();
|
||||||
|
for(i=0; i<imax; i++){
|
||||||
|
setPenColor(Color.GRAY);
|
||||||
|
line(M.get(i,0), M.get(i,1), M.get(i,2), M.get(i,3));
|
||||||
|
setPenColor(Color.RED);
|
||||||
|
line(M.get(i,0)+dM.get(i,0)*f, M.get(i,1)+dM.get(i,1)*f,
|
||||||
|
M.get(i,2)+dM.get(i,2)*f, M.get(i,3)+dM.get(i,3)*f);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("deprecation")
|
||||||
|
public void animate(){
|
||||||
|
if(!animationSet){
|
||||||
|
animateContents();
|
||||||
|
SwingUtilities.invokeLater(new Runnable() {
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
new Animate();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
animationSet = true;
|
||||||
|
} else contents();
|
||||||
|
if(plot!=null) plot.stop();
|
||||||
|
plot = new Thread(new Animate());
|
||||||
|
plot.start();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void animate(double[] X, double[] Y){
|
||||||
|
allocation(X, Y);
|
||||||
|
double dx = 0, dy = 0;
|
||||||
|
if(Maths.min(X) == Maths.max(X)) dx = 0.5;
|
||||||
|
if(Maths.min(Y) == Maths.max(Y)) dy = 0.5;
|
||||||
|
setScale(Maths.min(X)*1.1-dx, Maths.max(X)*1.1+dx,
|
||||||
|
Maths.min(Y)*1.1-dy, Maths.max(Y)*1.1+dy);
|
||||||
|
animate();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void animate(Vector X, Vector Y){
|
||||||
|
allocation(X, Y);
|
||||||
|
double[] x = X.getArray();
|
||||||
|
double[] y = Y.getArray();
|
||||||
|
double dx = 0, dy = 0;
|
||||||
|
if(Maths.min(x) == Maths.max(x)) dx = 0.5;
|
||||||
|
if(Maths.min(y) == Maths.max(y)) dy = 0.5;
|
||||||
|
setScale(Maths.min(x)*1.1-dx, Maths.max(x)*1.1+dx,
|
||||||
|
Maths.min(y)*1.1-dy, Maths.max(y)*1.1+dy);
|
||||||
|
animate();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void animate(Matrix X, Matrix Y){
|
||||||
|
allocation(X,Y);
|
||||||
|
setScale(X.min()*1.1, X.max()*1.1,
|
||||||
|
Y.min()*1.1, Y.max()*1.1);
|
||||||
|
animate();
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("deprecation")
|
||||||
|
public void animateLines(double[][] A, double[][] dA) {
|
||||||
|
M = new Matrix(A);
|
||||||
|
dM = new Matrix(dA);
|
||||||
|
if(!animationSet){
|
||||||
|
animateContents();
|
||||||
|
SwingUtilities.invokeLater(new Runnable() {
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
setPenColor(Color.LIGHT_GRAY);
|
||||||
|
new AnimateLines();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
animationSet = true;
|
||||||
|
} else contents();
|
||||||
|
setPenColor(Color.LIGHT_GRAY);
|
||||||
|
if(plot!=null) plot.stop();
|
||||||
|
plot = new Thread(new AnimateLines());
|
||||||
|
plot.start();
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: merge with animateLines -> class: DrawFEM?
|
||||||
|
@SuppressWarnings("deprecation")
|
||||||
|
public void animateFEM(double[][] A, double[][] dA, double[] a) {
|
||||||
|
M = new Matrix(A);
|
||||||
|
dM = new Matrix(dA);
|
||||||
|
m = new Vector(a);
|
||||||
|
// Display size
|
||||||
|
double xMin = M.getN(2).min();
|
||||||
|
double xMax = M.getN(2).max();
|
||||||
|
double yMin = M.getN(3).min();
|
||||||
|
double yMax = M.getN(3).max();
|
||||||
|
if(M.getN(0).min() < xMin) xMin = M.getN(0).min();
|
||||||
|
if(M.getN(0).max() > xMax) xMax = M.getN(0).max();
|
||||||
|
if(M.getN(1).min() < yMin) yMin = M.getN(1).min();
|
||||||
|
if(M.getN(1).max() > yMax) yMax = M.getN(1).max();
|
||||||
|
// System.out.println((xMax-xMin)+" "+(yMax-yMin));
|
||||||
|
// System.out.println(((xMax-xMin) - (yMax-yMin))/2);
|
||||||
|
// System.out.println(yMin+" "+yMax);
|
||||||
|
double xMM = xMax - xMin;
|
||||||
|
double yMM = yMax - yMin;
|
||||||
|
if((xMM) > (yMM)){
|
||||||
|
double dif = (xMM - yMM)/2;
|
||||||
|
yMin -= dif*1.05; // kleine Verschiebung nach oben
|
||||||
|
yMax += dif*0.95;
|
||||||
|
} else {
|
||||||
|
double dif = (yMM - xMM)/2;
|
||||||
|
xMin -= dif*1.05;
|
||||||
|
xMax += dif*0.95;
|
||||||
|
}
|
||||||
|
// System.out.println(yMin+" "+yMax);
|
||||||
|
// System.out.println((xMax-xMin)+" "+(yMax-yMin));
|
||||||
|
setScale(xMin, xMax, yMin, yMax);
|
||||||
|
// Displacement factor
|
||||||
|
double xdMM = dM.getN(2).max() - dM.getN(2).min();
|
||||||
|
double ydMM = dM.getN(3).max() - dM.getN(3).min();
|
||||||
|
double dMM = Math.sqrt(xdMM*xdMM+ydMM*ydMM);
|
||||||
|
double MM = Math.sqrt(xMM*xMM+yMM*yMM);
|
||||||
|
fac = MM/dMM/100*2;
|
||||||
|
if(fac<1)fac=1;
|
||||||
|
// System.out.println(dMM);
|
||||||
|
// System.out.println(MM);
|
||||||
|
System.out.printf("Scalierung %.4g%n",fac);
|
||||||
|
if(!animationSet){
|
||||||
|
animateContents();
|
||||||
|
SwingUtilities.invokeLater(new Runnable() {
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
setPenColor(Color.LIGHT_GRAY);
|
||||||
|
new AnimateFEM();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
animationSet = true;
|
||||||
|
} else contents();
|
||||||
|
setPenColor(Color.LIGHT_GRAY);
|
||||||
|
if(plot!=null) plot.stop();
|
||||||
|
plot = new Thread(new AnimateFEM());
|
||||||
|
plot.start();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void contents(){
|
||||||
|
frame.setLocation(100, 50);
|
||||||
|
|
||||||
|
setXscale(scaleLeft, scaleRight);
|
||||||
|
setYscale(scaleBottom, scaleTop);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void cross(){
|
||||||
|
setPenColor(Color.GRAY);
|
||||||
|
line(scaleLeft, 0, scaleRight, 0);
|
||||||
|
line(0, scaleBottom, 0, scaleTop);
|
||||||
|
setPenColor(getGraphColor());
|
||||||
|
}
|
||||||
|
|
||||||
|
private void animateContents(){
|
||||||
|
contents();
|
||||||
|
infoLabel = new JLabel("0 %");
|
||||||
|
infoLabel.setHorizontalAlignment(SwingConstants.RIGHT);
|
||||||
|
infoLabel.setBounds(DEFAULT_SIZE+left-107, top+5, 100, 20);
|
||||||
|
frame.add(infoLabel);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Initialize Nyquist data
|
||||||
|
*/
|
||||||
|
private void nyquist(){
|
||||||
|
frame.setTitle("Nyquist");
|
||||||
|
Nyquist nyq = new Nyquist();
|
||||||
|
Draw.X = nyq.getNyquist().getN(0).getArray();
|
||||||
|
Draw.Y = nyq.getNyquist().getN(1).getArray();
|
||||||
|
|
||||||
|
scaleLeft = -1.5;
|
||||||
|
scaleRight = 2.5;
|
||||||
|
scaleBottom = -2.5;
|
||||||
|
scaleTop = 1.5;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Plot Nyquist
|
||||||
|
*/
|
||||||
|
public void plotNyquist() {
|
||||||
|
nyquist();
|
||||||
|
plot();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Animate Nyquist
|
||||||
|
*/
|
||||||
|
public void animateNyquist() {
|
||||||
|
nyquist();
|
||||||
|
animate();
|
||||||
|
cross();
|
||||||
|
//TODO:mark?
|
||||||
|
markX(-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public class Animate implements Runnable{
|
||||||
|
@Override
|
||||||
|
public void run(){
|
||||||
|
if(XM != null && YM != null){
|
||||||
|
// TODO: different Color
|
||||||
|
Color[] color = new Color[]{
|
||||||
|
Color.LIGHT_BLUE,
|
||||||
|
Color.PURPLE,
|
||||||
|
Color.YELLOW,
|
||||||
|
Color.GREEN,
|
||||||
|
Color.RED};
|
||||||
|
int i, j;
|
||||||
|
int imax = XM.getM();
|
||||||
|
int jmax = XM.getN();
|
||||||
|
int max = imax > jmax ? imax : jmax;
|
||||||
|
int sec = (int) 1000./max*10;
|
||||||
|
sec = sec > 10 ? 10 : sec;
|
||||||
|
// System.out.println(max);
|
||||||
|
// System.out.println(sec);
|
||||||
|
for(j=0; j<jmax; j++){
|
||||||
|
for(i=0; i<imax; i++){
|
||||||
|
// setPenColor(color[((int) (Math.pow(-1, i)))<0?0:1]);
|
||||||
|
if(i>=color.length) setPenColor(color[0]);
|
||||||
|
else setPenColor(color[i]);
|
||||||
|
point(XM.get(i,j), YM.get(i,j));
|
||||||
|
show(sec);
|
||||||
|
setProcess((double)(i+j+1)/(imax+jmax)*100);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if(X!=null){
|
||||||
|
int i;
|
||||||
|
int imax = X.length;
|
||||||
|
int sec = (int) 1000./imax*10;
|
||||||
|
sec = sec > 10 ? 10 : sec;
|
||||||
|
// System.out.println(imax);
|
||||||
|
// System.out.println(sec);
|
||||||
|
for(i=0; i<imax; i++){
|
||||||
|
point(X[i], Y[i]);
|
||||||
|
show(sec);
|
||||||
|
// System.out.println(X[i]);
|
||||||
|
setProcess((double)(i+1)/imax*100);
|
||||||
|
// System.out.println(process);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public class AnimateLines implements Runnable{
|
||||||
|
@Override
|
||||||
|
public void run(){
|
||||||
|
if(M!=null){
|
||||||
|
int i, j;
|
||||||
|
int imax = M.getM();
|
||||||
|
int jmax = 200;
|
||||||
|
double f;
|
||||||
|
for(j=0; j<jmax; j++){
|
||||||
|
f = (double)(j+1)/jmax * 50;
|
||||||
|
// System.out.println(f);
|
||||||
|
clear();
|
||||||
|
for(i=0; i<imax; i++){
|
||||||
|
setPenColor(Color.GRAY);
|
||||||
|
line(M.get(i,0), M.get(i,1), M.get(i,2), M.get(i,3));
|
||||||
|
setPenColor(Color.RED);
|
||||||
|
line(M.get(i,0)+dM.get(i,0)*f, M.get(i,1)+dM.get(i,1)*f,
|
||||||
|
M.get(i,2)+dM.get(i,2)*f, M.get(i,3)+dM.get(i,3)*f);
|
||||||
|
}
|
||||||
|
show(10);
|
||||||
|
setProcess((double)(i+j+1)/(imax+jmax)*100);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
// TODO: merge with animateLines -> class: DrawFEM?
|
||||||
|
public class AnimateFEM implements Runnable{
|
||||||
|
@Override
|
||||||
|
public void run(){
|
||||||
|
if(M!=null){
|
||||||
|
int i, j;
|
||||||
|
int imax = M.getM();
|
||||||
|
int jmax = 200;
|
||||||
|
int mMax = m.abs().indexOfMax();
|
||||||
|
double max = m.max();
|
||||||
|
double min = m.min();
|
||||||
|
double f;
|
||||||
|
for(j=0; j<jmax; j++){
|
||||||
|
f = (double)(j+1)/jmax * fac;
|
||||||
|
// System.out.println(f);
|
||||||
|
clear();
|
||||||
|
for(i=0; i<imax; i++){
|
||||||
|
setPenColor(Color.GRAY);
|
||||||
|
line(M.get(i,0), M.get(i,1), M.get(i,2), M.get(i,3));
|
||||||
|
if(i == mMax) setPenColor(Color.RED);
|
||||||
|
else if(m.get(i) >= 0.92*max) setPenColor(Color.ORANGE);
|
||||||
|
else if(m.get(i) >= 0.81*max) setPenColor(Color.YELLOW);
|
||||||
|
else if(m.get(i) >= 0.67*max) setPenColor(Color.GREEN);
|
||||||
|
else if(m.get(i) >= 0.50*max) setPenColor(Color.GREEN);
|
||||||
|
else if(m.get(i) >= 0.30*max) setPenColor(Color.GREEN);
|
||||||
|
else if(m.get(i) > 0.30*min) setPenColor(Color.GREEN);
|
||||||
|
else if(m.get(i) > 0.50*min) setPenColor(Color.GREEN);
|
||||||
|
else if(m.get(i) > 0.67*min) setPenColor(Color.GREEN);
|
||||||
|
else if(m.get(i) > 0.81*min) setPenColor(Color.GREEN);
|
||||||
|
else if(m.get(i) > 0.92*min) setPenColor(Color.CYAN);
|
||||||
|
else if(m.get(i) > 1.00*min) setPenColor(Color.BLUE);
|
||||||
|
else setPenColor(Color.PURPLE);
|
||||||
|
line(M.get(i,0)+dM.get(i,0)*f, M.get(i,1)+dM.get(i,1)*f,
|
||||||
|
M.get(i,2)+dM.get(i,2)*f, M.get(i,3)+dM.get(i,3)*f);
|
||||||
|
}
|
||||||
|
show(10);
|
||||||
|
setProcess((double)(i+j+1)/(imax+jmax)*100);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("deprecation")
|
||||||
|
public void stop(){
|
||||||
|
plot.stop();
|
||||||
|
// plot.interrupt();
|
||||||
|
// frame.repaint(); // bringt nichts
|
||||||
|
// frame.removeAll();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void markX(double x){
|
||||||
|
double size = (scaleTop-scaleBottom)*.01;
|
||||||
|
line(x, -size, x, size);
|
||||||
|
if(x!=0)
|
||||||
|
if(scaleLeft==0) text(x, 3*size, String.format("%.1f", x));
|
||||||
|
else text(x, -4*size, String.format("%.1f", x));
|
||||||
|
}
|
||||||
|
|
||||||
|
public void markY(double y){
|
||||||
|
double size = (scaleRight-scaleLeft)*.01;
|
||||||
|
line(-size, y, size, y);
|
||||||
|
if(y!=0)
|
||||||
|
if(scaleBottom==0) textLeft(2*size, y, String.format("%.1f", y));
|
||||||
|
else textRight(-2.5*size, y, String.format("%.1f", y));
|
||||||
|
}
|
||||||
|
|
||||||
|
public void mark(double x, double y){
|
||||||
|
double sizeX = (scaleTop-scaleBottom)*.01;
|
||||||
|
double sizeY = (scaleRight-scaleLeft)*.01;
|
||||||
|
filledCircle(x, y, sizeX<sizeY?sizeX:sizeY);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param args
|
||||||
|
*/
|
||||||
|
public static void main(String[] args) {
|
||||||
|
// new Draw();
|
||||||
|
// new Draw().plotNyquist();
|
||||||
|
new Draw().animateNyquist();
|
||||||
|
// new Draw().animate();
|
||||||
|
}
|
||||||
|
}
|
||||||
1195
src/math/equation/Polynomial.java
Normal file
1195
src/math/equation/Polynomial.java
Normal file
File diff suppressed because it is too large
Load Diff
114
src/math/equation/PolynomialComplex.java
Normal file
114
src/math/equation/PolynomialComplex.java
Normal file
@@ -0,0 +1,114 @@
|
|||||||
|
package math.equation;
|
||||||
|
|
||||||
|
import math.number.NumberComplex;
|
||||||
|
|
||||||
|
|
||||||
|
public class PolynomialComplex {
|
||||||
|
private Polynomial re;
|
||||||
|
private Polynomial im;
|
||||||
|
|
||||||
|
public PolynomialComplex(){
|
||||||
|
setRe(new Polynomial());
|
||||||
|
im = new Polynomial();
|
||||||
|
}
|
||||||
|
|
||||||
|
public PolynomialComplex(String cpol){
|
||||||
|
this(new Polynomial(cpol));
|
||||||
|
}
|
||||||
|
|
||||||
|
public PolynomialComplex(Polynomial c){
|
||||||
|
int i;
|
||||||
|
for(i=0; i<=c.degree(); i++){
|
||||||
|
// TODO:
|
||||||
|
}
|
||||||
|
|
||||||
|
int size = c.degree()+1;
|
||||||
|
double[] coefRe = new double[size];
|
||||||
|
double[] coefIm = new double[size];
|
||||||
|
for(i=0; i<size; i++){
|
||||||
|
if(i%2 == 0)
|
||||||
|
coefRe[size-i-1] = c.getCoef(i)*Math.pow(-1,i/2);
|
||||||
|
if(i%2 == 1)
|
||||||
|
coefIm[size-i-1] = c.getCoef(i)*Math.pow(-1,i/2);
|
||||||
|
}
|
||||||
|
setRe(new Polynomial(coefRe));
|
||||||
|
im = new Polynomial(coefIm);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public PolynomialComplex(Polynomial re, Polynomial im){
|
||||||
|
this.re = re;
|
||||||
|
this.im = im;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* set the symbolic of all polynomials
|
||||||
|
* @param symb symbolic
|
||||||
|
*/
|
||||||
|
public void setSymbolic(String symb){
|
||||||
|
re.setSymbolic(symb);
|
||||||
|
im.setSymbolic(symb);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* a + ib, a=Re(f(x)), b=Im(f(x))
|
||||||
|
* @param x
|
||||||
|
*/
|
||||||
|
public NumberComplex evaluate(double x){
|
||||||
|
return new NumberComplex(re.evaluate(x), im.evaluate(x));
|
||||||
|
}
|
||||||
|
|
||||||
|
public double mod(double x){
|
||||||
|
return evaluate(x).mod();
|
||||||
|
}
|
||||||
|
|
||||||
|
public double argd(double x){
|
||||||
|
return evaluate(x).argd();
|
||||||
|
}
|
||||||
|
|
||||||
|
public Polynomial getRe() {
|
||||||
|
return re;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRe(Polynomial re) {
|
||||||
|
this.re = re;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Polynomial getIm() {
|
||||||
|
return im;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setIm(Polynomial im) {
|
||||||
|
this.im = im;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString(){
|
||||||
|
if(getRe().degree() == 0 && im.degree() == 0){
|
||||||
|
if(im.getCoef(0) == 0) return ""+getRe();
|
||||||
|
if(getRe().getCoef(0) == 0) return im+"i";
|
||||||
|
return ""+getRe()+" + "+im+"i";
|
||||||
|
}
|
||||||
|
return "("+getRe()+") + ("+im+")i";
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param args
|
||||||
|
*/
|
||||||
|
public static void main(String[] args) {
|
||||||
|
Polynomial pol = new Polynomial("576 240 24 0");
|
||||||
|
pol.setSymbolic("s");
|
||||||
|
System.out.println(" G(s) = "+pol);
|
||||||
|
|
||||||
|
PolynomialComplex cpol = new PolynomialComplex(pol);
|
||||||
|
cpol.setSymbolic("ω");
|
||||||
|
System.out.println(" G(jω) = "+cpol);
|
||||||
|
|
||||||
|
NumberComplex cn = cpol.evaluate(0.01);
|
||||||
|
System.out.println(" G(2) = "+cn);
|
||||||
|
|
||||||
|
System.out.println("|G(2)| = "+cn.mod());
|
||||||
|
System.out.println("phi(2) = "+cn.argd());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
128
src/math/equation/RationalPolynomial.java
Normal file
128
src/math/equation/RationalPolynomial.java
Normal file
@@ -0,0 +1,128 @@
|
|||||||
|
package math.equation;
|
||||||
|
|
||||||
|
|
||||||
|
public class RationalPolynomial {
|
||||||
|
public Polynomial a;
|
||||||
|
public Polynomial b;
|
||||||
|
|
||||||
|
public RationalPolynomial(){
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomial(Polynomial a, Polynomial b){
|
||||||
|
this.a = a;
|
||||||
|
this.b = b;
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomial(Polynomial a, String b){
|
||||||
|
this.a = a;
|
||||||
|
this.b = new Polynomial(b);
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomial(String a, Polynomial b){
|
||||||
|
this.a = new Polynomial(a);
|
||||||
|
this.b = b;
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomial(String a, String b){
|
||||||
|
this.a = new Polynomial(a);
|
||||||
|
this.b = new Polynomial(b);
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomial(double a, String b){
|
||||||
|
this.a = new Polynomial(a);
|
||||||
|
this.b = new Polynomial(b);
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomial(double a, double b){
|
||||||
|
this.a = new Polynomial(a);
|
||||||
|
this.b = new Polynomial(b);
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomial(String ab){
|
||||||
|
String[] a_b = ab.split(";");
|
||||||
|
if(a_b.length == 1){
|
||||||
|
a = new Polynomial(a_b[0]);
|
||||||
|
b = new Polynomial(1);
|
||||||
|
}
|
||||||
|
if(a_b.length == 2){
|
||||||
|
a = new Polynomial(a_b[0]);
|
||||||
|
b = new Polynomial(a_b[1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* set the symbolic of all polynomials
|
||||||
|
* @param symb symbolic
|
||||||
|
*/
|
||||||
|
public void setSymbolic(String symb){
|
||||||
|
a.setSymbolic(symb);
|
||||||
|
b.setSymbolic(symb);
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomial plus(RationalPolynomial g){
|
||||||
|
Polynomial a = new Polynomial(this.a.times(g.b)).plus((g.a.times(b)));
|
||||||
|
Polynomial b = new Polynomial(this.b.times(g.b));
|
||||||
|
return new RationalPolynomial(a, b);
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomial minus(RationalPolynomial g){
|
||||||
|
Polynomial a = new Polynomial(this.a.times(g.b)).minus((g.a.times(b)));
|
||||||
|
Polynomial b = new Polynomial(this.b.times(g.b));
|
||||||
|
return new RationalPolynomial(a, b);
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomial times(RationalPolynomial g){
|
||||||
|
Polynomial a = new Polynomial(this.a).times(g.a);
|
||||||
|
Polynomial b = new Polynomial(this.b).times(g.b);
|
||||||
|
return new RationalPolynomial(a, b);
|
||||||
|
}
|
||||||
|
|
||||||
|
// use Horner's method to compute and return the polynomial evaluated at x
|
||||||
|
public double evaluate(double x){
|
||||||
|
return a.evaluate(x) / b.evaluate(x);
|
||||||
|
}
|
||||||
|
|
||||||
|
public double mod(double x){
|
||||||
|
return new RationalPolynomialComplex(this).mod(x);
|
||||||
|
}
|
||||||
|
|
||||||
|
public double argd(double x){
|
||||||
|
return new RationalPolynomialComplex(this).argd(x);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString(){
|
||||||
|
String p = ""+a;
|
||||||
|
String q = ""+b;
|
||||||
|
int size = p.length() > q.length() ? p.length() : q.length();
|
||||||
|
String sep = "";
|
||||||
|
for(int i=0; i<size; i++)
|
||||||
|
sep += "-";
|
||||||
|
String s = p+"\n";
|
||||||
|
if(b.getCoef(0) != 1 || b.degree() != 0) s += sep+"\n" + q+"\n";
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void main(String[] args){
|
||||||
|
RationalPolynomial PT1 = new RationalPolynomial("2; 4 1");
|
||||||
|
PT1.setSymbolic("ω");
|
||||||
|
System.out.println(PT1);
|
||||||
|
|
||||||
|
RationalPolynomial PT2 = new RationalPolynomial("1; 6 1");
|
||||||
|
PT2.setSymbolic("ω");
|
||||||
|
System.out.println(PT2);
|
||||||
|
|
||||||
|
RationalPolynomial I = new RationalPolynomial(5,"24 0");
|
||||||
|
I.setSymbolic("ω");
|
||||||
|
System.out.println(I);
|
||||||
|
|
||||||
|
RationalPolynomial sys = PT1.times(PT2).times(I);
|
||||||
|
sys.setSymbolic("ω");
|
||||||
|
System.out.println(sys);
|
||||||
|
|
||||||
|
System.out.println("|G(1)| = "+sys.mod(1)+"\n");
|
||||||
|
|
||||||
|
System.out.println("phi(1) = "+sys.argd(1));
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
112
src/math/equation/RationalPolynomialComplex.java
Normal file
112
src/math/equation/RationalPolynomialComplex.java
Normal file
@@ -0,0 +1,112 @@
|
|||||||
|
package math.equation;
|
||||||
|
|
||||||
|
import math.number.NumberComplex;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* quotient
|
||||||
|
* a(x) + b(x)i / c(x) + d(x)i
|
||||||
|
* @author Daniel
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public class RationalPolynomialComplex {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Dividend / numerator
|
||||||
|
*/
|
||||||
|
private PolynomialComplex a;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Divisor / denominator
|
||||||
|
*/
|
||||||
|
private PolynomialComplex b;
|
||||||
|
|
||||||
|
public RationalPolynomialComplex(){
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomialComplex(RationalPolynomial f){
|
||||||
|
setDivident(new PolynomialComplex(f.a));
|
||||||
|
b = new PolynomialComplex(f.b);
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomialComplex(String cpol){
|
||||||
|
String[] ri = cpol.split(";");
|
||||||
|
int size = ri.length;
|
||||||
|
if(size == 1){
|
||||||
|
setDivident(new PolynomialComplex(ri[0]));
|
||||||
|
// b = new ComplexPolynomial();
|
||||||
|
}
|
||||||
|
if(size == 2){
|
||||||
|
setDivident(new PolynomialComplex(ri[0]));
|
||||||
|
b = new PolynomialComplex(ri[1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public RationalPolynomialComplex(PolynomialComplex a, PolynomialComplex b){
|
||||||
|
this.a = a;
|
||||||
|
this.b = b;
|
||||||
|
}
|
||||||
|
|
||||||
|
public NumberComplex evaluate(double x){
|
||||||
|
return a.evaluate(x).over(b.evaluate(x));
|
||||||
|
// return new RationalComplex(a.evaluate(x),b.evaluate(x)));
|
||||||
|
}
|
||||||
|
|
||||||
|
public double mod(double x){
|
||||||
|
return a.mod(x)/b.mod(x);
|
||||||
|
}
|
||||||
|
|
||||||
|
public double argd(double x){
|
||||||
|
return evaluate(x).argd();
|
||||||
|
}
|
||||||
|
|
||||||
|
public PolynomialComplex getDivident() {
|
||||||
|
return a;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setDivident(PolynomialComplex a) {
|
||||||
|
this.a = a;
|
||||||
|
}
|
||||||
|
|
||||||
|
public PolynomialComplex getDivisor() {
|
||||||
|
return b;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setDivisor(PolynomialComplex b) {
|
||||||
|
this.b = b;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* set the symbolic of all polynomials
|
||||||
|
* @param symb symbolic
|
||||||
|
*/
|
||||||
|
public void setSymbolic(String symb){
|
||||||
|
a.setSymbolic(symb);
|
||||||
|
b.setSymbolic(symb);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString(){
|
||||||
|
String p = ""+getDivident();
|
||||||
|
String q = ""+b;
|
||||||
|
int size = p.length() > q.length() ? p.length() : q.length();
|
||||||
|
String sep = "";
|
||||||
|
for(int i=0; i<size; i++)
|
||||||
|
sep += "-";
|
||||||
|
String s = p+"\n";
|
||||||
|
if(b.getRe().getCoef(0) != 1 || b.getRe().degree() != 0) s += sep+"\n" + q+"\n";
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param args
|
||||||
|
*/
|
||||||
|
public static void main(String[] args) {
|
||||||
|
RationalPolynomialComplex cpol = new RationalPolynomialComplex("10; 576 240 24 0");
|
||||||
|
cpol.setSymbolic("ω");
|
||||||
|
System.out.println(cpol);
|
||||||
|
NumberComplex cn = cpol.evaluate(0.125);
|
||||||
|
System.out.println(cn);
|
||||||
|
System.out.println(cn.mod());
|
||||||
|
System.out.println(cn.argd());
|
||||||
|
}
|
||||||
|
}
|
||||||
513
src/math/matrix/VectorComplex.java
Normal file
513
src/math/matrix/VectorComplex.java
Normal file
@@ -0,0 +1,513 @@
|
|||||||
|
package math.matrix;
|
||||||
|
|
||||||
|
import math.number.NumberComplex;
|
||||||
|
import thisandthat.WObject;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Complex vector v<sub>i</sub>∈ℂ
|
||||||
|
* @author Daniel
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public class VectorComplex extends WObject{
|
||||||
|
/**
|
||||||
|
* a<sub>i0</sub> = real ℜ,
|
||||||
|
* a<sub>i1</sub> = imaginary ℑ
|
||||||
|
*/
|
||||||
|
private double[][] vector;
|
||||||
|
|
||||||
|
public VectorComplex(){
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create zero vector
|
||||||
|
* @param n rows
|
||||||
|
*/
|
||||||
|
public VectorComplex(int n){
|
||||||
|
vector = new double[n][2];
|
||||||
|
int i;
|
||||||
|
for(i=0; i<n; i++){
|
||||||
|
vector[i][0] = 0;
|
||||||
|
vector[i][1] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with given x
|
||||||
|
* @param x
|
||||||
|
*/
|
||||||
|
public VectorComplex(double x){
|
||||||
|
vector = new double[][]{{x,0}};
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with given x
|
||||||
|
* @param x
|
||||||
|
*/
|
||||||
|
public VectorComplex(NumberComplex x){
|
||||||
|
vector = new double[][]{{x.ℜ(),x.ℑ()}};
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with given x and y value
|
||||||
|
* @param x
|
||||||
|
* @param y
|
||||||
|
*/
|
||||||
|
public VectorComplex(NumberComplex x, NumberComplex y){
|
||||||
|
vector = new double[][]{{x.ℜ(),x.ℑ()}, {y.ℜ(),y.ℑ()}};
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with given x, y and z value
|
||||||
|
* @param x
|
||||||
|
* @param y
|
||||||
|
* @param z
|
||||||
|
*/
|
||||||
|
public VectorComplex(NumberComplex x, NumberComplex y, NumberComplex z){
|
||||||
|
vector = new double[][]{{x.ℜ(),x.ℑ()}, {y.ℜ(),y.ℑ()}, {z.ℜ(),z.ℑ()}};
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with given array
|
||||||
|
* @param v array
|
||||||
|
*/
|
||||||
|
public VectorComplex(double[] v){
|
||||||
|
int i;
|
||||||
|
int n = v.length;
|
||||||
|
vector = new double[n][2];
|
||||||
|
for(i=0; i<n; i++)
|
||||||
|
vector[i][0] = v[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with given arrays
|
||||||
|
* @param real array
|
||||||
|
* @param imag array
|
||||||
|
*/
|
||||||
|
public VectorComplex(double[] real, double[] imag){
|
||||||
|
int i;
|
||||||
|
int n = real.length;
|
||||||
|
vector = new double[n][2];
|
||||||
|
for(i=0; i<n; i++){
|
||||||
|
vector[i][0] = real[i];
|
||||||
|
vector[i][1] = imag[i];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with given double array
|
||||||
|
* @param v double array
|
||||||
|
*/
|
||||||
|
public VectorComplex(double[][] v){
|
||||||
|
int i;
|
||||||
|
int n = v.length;
|
||||||
|
vector = new double[n][2];
|
||||||
|
for(i=0; i<n; i++){
|
||||||
|
vector[i][0] = v[i][0];
|
||||||
|
vector[i][1] = v[i][1];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Copy vector
|
||||||
|
* @param v vector
|
||||||
|
*/
|
||||||
|
public VectorComplex(VectorComplex v){
|
||||||
|
this(v.vector);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return vector array
|
||||||
|
*/
|
||||||
|
public double[][] get(){
|
||||||
|
return vector;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param i index
|
||||||
|
* @return value
|
||||||
|
* @see #getRe(int)
|
||||||
|
* @see #getIm(int)
|
||||||
|
*/
|
||||||
|
public NumberComplex get(int i){
|
||||||
|
return new NumberComplex(vector[i][0],vector[i][1]);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* get real value at index
|
||||||
|
* @param i index
|
||||||
|
* @return value
|
||||||
|
* @see #get(int)
|
||||||
|
* @see #getIm(int)
|
||||||
|
*/
|
||||||
|
public double getRe(int i){
|
||||||
|
return vector[i][0];
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* get real value at index
|
||||||
|
* @param i index
|
||||||
|
* @return value
|
||||||
|
* @see #get(int)
|
||||||
|
* @see #getRe(int)
|
||||||
|
*/
|
||||||
|
public double getIm(int i){
|
||||||
|
return vector[i][0];
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* set value at index
|
||||||
|
* @param i index
|
||||||
|
* @param re real value
|
||||||
|
* @param im imaginary value
|
||||||
|
*/
|
||||||
|
public void set(int i, double re, double im){
|
||||||
|
vector[i][0] = re;
|
||||||
|
vector[i][1] = im;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* set value at index
|
||||||
|
* @param i index
|
||||||
|
* @param a value
|
||||||
|
*/
|
||||||
|
public void set(int i, NumberComplex a){
|
||||||
|
set(i, a.ℜ(), a.ℑ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* get x (first element)
|
||||||
|
* @return x value
|
||||||
|
*/
|
||||||
|
public NumberComplex x(){
|
||||||
|
return n()>0 ? new NumberComplex(vector[0][0],vector[0][1]) : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* get y (second element)
|
||||||
|
* @return y value
|
||||||
|
*/
|
||||||
|
public NumberComplex y(){
|
||||||
|
return n()>1 ? new NumberComplex(vector[1][0],vector[1][1]) : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* get z (third element)
|
||||||
|
* @return z value
|
||||||
|
*/
|
||||||
|
public NumberComplex z(){
|
||||||
|
return n()>2 ? new NumberComplex(vector[2][0],vector[2][1]) : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with zeros
|
||||||
|
* @param n size
|
||||||
|
* @return zero vector
|
||||||
|
*/
|
||||||
|
public static VectorComplex zeros(int n){
|
||||||
|
return new VectorComplex(n);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with ones
|
||||||
|
* @param n size
|
||||||
|
* @return one vector
|
||||||
|
*/
|
||||||
|
public static VectorComplex ones(int n){
|
||||||
|
return fill(n, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with given complex number
|
||||||
|
* @param n size
|
||||||
|
* @param s real number
|
||||||
|
* @return complex vector filled with real numbers
|
||||||
|
*/
|
||||||
|
public static VectorComplex fill(int n, double s){
|
||||||
|
return fill(n, s, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with given real and imaginary part
|
||||||
|
* @param n size
|
||||||
|
* @param r real
|
||||||
|
* @param i imaginary
|
||||||
|
* @return vector filled with complex numbers
|
||||||
|
*/
|
||||||
|
public static VectorComplex fill(int n, double r, double i){
|
||||||
|
VectorComplex a = new VectorComplex(n);
|
||||||
|
int j;
|
||||||
|
for(j=0; j<n; j++){
|
||||||
|
a.vector[j][0] = r;
|
||||||
|
a.vector[j][0] = i;
|
||||||
|
}
|
||||||
|
return a;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector with given complex number
|
||||||
|
* @param n size
|
||||||
|
* @param z complex number
|
||||||
|
* @return vector filled with complex numbers
|
||||||
|
*/
|
||||||
|
public static VectorComplex fill(int n, NumberComplex z){
|
||||||
|
return fill(n, z.ℜ(), z.ℑ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector and fill it from a start value to an end value
|
||||||
|
* @param start
|
||||||
|
* @param end
|
||||||
|
* @return filled vector [start,start+1,...,end]
|
||||||
|
*/
|
||||||
|
public static VectorComplex fill(NumberComplex start, NumberComplex end){
|
||||||
|
double deltaRe = end.ℜ()-start.ℜ();
|
||||||
|
double deltaIm = end.ℑ()-start.ℑ();
|
||||||
|
NumberComplex increment = new NumberComplex(
|
||||||
|
deltaRe>1 ? 1 : deltaRe<-1 ? -1 : 0,
|
||||||
|
deltaIm>1 ? 1 : deltaIm<-1 ? -1 : 0);
|
||||||
|
return fill(start, increment, end);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create vector and fill it from a start value and increments it to an end value
|
||||||
|
* @param start
|
||||||
|
* @param increment
|
||||||
|
* @param end
|
||||||
|
* @return filled vector [start,start+increment,start+2*increment,...,end]
|
||||||
|
*/
|
||||||
|
public static VectorComplex fill(NumberComplex start, NumberComplex increment, NumberComplex end){
|
||||||
|
double deltaRe = end.ℜ()-start.ℜ();
|
||||||
|
double deltaIm = end.ℑ()-start.ℑ();
|
||||||
|
int nRe = increment.ℜ()!=0?(int)(deltaRe/increment.ℜ())+1:0;
|
||||||
|
int nIm = increment.ℑ()!=0?(int)(deltaIm/increment.ℑ())+1:0;
|
||||||
|
int n = nRe > nIm ? nRe : nIm;
|
||||||
|
if(n==0||(deltaRe>=0&&increment.ℜ()<0&&deltaIm>=0&&increment.ℑ()<0)||
|
||||||
|
(deltaRe<0&&increment.ℜ()>=0&&deltaIm<0&&increment.ℑ()>=0)||
|
||||||
|
(increment.ℜ()==0&&increment.ℑ()==0)) return new VectorComplex(start);
|
||||||
|
VectorComplex a = new VectorComplex(n);
|
||||||
|
int i;
|
||||||
|
for(i=0; i<n; i++){
|
||||||
|
a.vector[i][0] = start.ℜ() + i*increment.ℜ();
|
||||||
|
a.vector[i][1] = start.ℑ() + i*increment.ℑ();
|
||||||
|
}
|
||||||
|
return a;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create zero vector and fill it with given values at given indices
|
||||||
|
* @param n
|
||||||
|
* @param indeces
|
||||||
|
* @param a value vector
|
||||||
|
* @return filled vector
|
||||||
|
*/
|
||||||
|
public static VectorComplex fill(int n, int[] indeces, VectorComplex a){
|
||||||
|
VectorComplex c = new VectorComplex(n);
|
||||||
|
for(int i=0; i<indeces.length; i++){
|
||||||
|
c.vector[indeces[i]-1][0] = a.vector[i][0];
|
||||||
|
c.vector[indeces[i]-1][1] = a.vector[i][1];
|
||||||
|
}
|
||||||
|
return c;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Fill vector with given values at given indices
|
||||||
|
* @param indices
|
||||||
|
* @param a value vector
|
||||||
|
*/
|
||||||
|
public void fill(int[] indices, VectorComplex a){
|
||||||
|
for(int i=0; i<indices.length; i++){
|
||||||
|
vector[indices[i]][0] = a.vector[i][0];
|
||||||
|
vector[indices[i]][1] = a.vector[i][1];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return dimension
|
||||||
|
*/
|
||||||
|
public int n(){
|
||||||
|
return vector.length;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return length or magnitude or norm
|
||||||
|
*/
|
||||||
|
public double norm(){
|
||||||
|
int i;
|
||||||
|
double x=0;
|
||||||
|
for(i=0; i<vector.length; i++)
|
||||||
|
x += vector[i][0]*vector[i][0] + vector[i][1]*vector[i][1];
|
||||||
|
return Math.sqrt(x);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* add a Vector.
|
||||||
|
* @param a vector to add
|
||||||
|
* @return added Vector
|
||||||
|
*/
|
||||||
|
public VectorComplex plus(VectorComplex a){
|
||||||
|
int i;
|
||||||
|
VectorComplex c = new VectorComplex(n());
|
||||||
|
for(i=0; i<n(); i++){
|
||||||
|
c.vector[i][0] = vector[i][0] + a.vector[i][0];
|
||||||
|
c.vector[i][1] = vector[i][1] + a.vector[i][1];
|
||||||
|
}
|
||||||
|
return c;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* add a Vector.
|
||||||
|
* @param s as vector to add
|
||||||
|
* @return added Vector
|
||||||
|
*/
|
||||||
|
public VectorComplex plus(NumberComplex s){
|
||||||
|
return plus(VectorComplex.fill(n(), s));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* subtract a Vector.
|
||||||
|
* @param a vector to subtract
|
||||||
|
* @return subtracted Vector
|
||||||
|
*/
|
||||||
|
public VectorComplex minus(VectorComplex a){
|
||||||
|
return plus(a.timesE(VectorComplex.fill(n(),new NumberComplex(-1,-1))));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Subtract a Vector.
|
||||||
|
* @param s as vector to subtract
|
||||||
|
* @return subtracted Vector
|
||||||
|
*/
|
||||||
|
public VectorComplex minus(NumberComplex s){
|
||||||
|
return plus(VectorComplex.fill(n(), s.times(new NumberComplex(-1,-1))));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Multiplicate the vector element wise.
|
||||||
|
* @param a vector
|
||||||
|
* @return element-wise multiplicated vector
|
||||||
|
*/
|
||||||
|
public VectorComplex timesE(VectorComplex a){
|
||||||
|
int i;
|
||||||
|
VectorComplex c = new VectorComplex(n());
|
||||||
|
for(i=0; i<n(); i++)
|
||||||
|
c.set(i, get(i).times(a.get(i)));
|
||||||
|
return c;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Divide the vector element wise
|
||||||
|
* @param a vector
|
||||||
|
* @return element-wise divided vector
|
||||||
|
*/
|
||||||
|
public VectorComplex overE(VectorComplex a){
|
||||||
|
int i;
|
||||||
|
VectorComplex c = new VectorComplex(n());
|
||||||
|
for(i=0; i<n(); i++)
|
||||||
|
c.set(i, get(i).over(a.get(i)));
|
||||||
|
return c;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* revolve vector 90°. max 2 dimension vector.
|
||||||
|
* @return 90° revolved vector
|
||||||
|
*/
|
||||||
|
public VectorComplex orthogonal(){
|
||||||
|
//TODO: ???
|
||||||
|
return new VectorComplex(get(1),get(0));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates a sub vector only with chosen rows
|
||||||
|
* @param indices rows
|
||||||
|
* @return the sub vector
|
||||||
|
*/
|
||||||
|
public VectorComplex subVector(int[] indices){
|
||||||
|
int n = indices.length;
|
||||||
|
VectorComplex red = new VectorComplex(n);
|
||||||
|
for(int i=0; i<n; i++){
|
||||||
|
red.vector[i][0] = vector[indices[i]-1][0];
|
||||||
|
red.vector[i][1] = vector[indices[i]-1][1];
|
||||||
|
}
|
||||||
|
return new VectorComplex(red);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find value in vector
|
||||||
|
* @return index
|
||||||
|
*/
|
||||||
|
public int find(NumberComplex a){
|
||||||
|
int i;
|
||||||
|
for(i=0; i<n(); i++)
|
||||||
|
if(a == get(i)) return i;
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isZero(){
|
||||||
|
int i;
|
||||||
|
boolean result = true;
|
||||||
|
for(i=0; i<n(); i++){
|
||||||
|
if(vector[i][0] > 0){
|
||||||
|
result = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if(vector[i][1] > 0){
|
||||||
|
result = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString(){
|
||||||
|
int i;
|
||||||
|
String output = "";
|
||||||
|
if(vector!=null){
|
||||||
|
for(i=0; i<n(); i++) {
|
||||||
|
vector[i] = (vector[i][0] <= 0.0 && vector[i][0]>-1E-10) ? null : vector[i];
|
||||||
|
output += String.format("% 10.4g % 10.4gi \n", vector[i][0], vector[i][1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return output;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Transpose (horizontal)
|
||||||
|
* @return string of vector in transposed form
|
||||||
|
*/
|
||||||
|
public String toStringT(){
|
||||||
|
int i;
|
||||||
|
String output = "";
|
||||||
|
if(vector!=null){
|
||||||
|
for(i=0; i<n(); i++) {
|
||||||
|
vector[i] = (vector[i][0] <= 0.0 && vector[i][0]>-1E-10) ? null : vector[i];
|
||||||
|
output += String.format("% 10.4g % 10.4gi ", vector[i][0], vector[i][1]);
|
||||||
|
}
|
||||||
|
output += "\n";
|
||||||
|
}
|
||||||
|
return output;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Transpose (horizontal)
|
||||||
|
*/
|
||||||
|
public void toConsoleT(){
|
||||||
|
System.out.println(toStringT());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* test client
|
||||||
|
* @param args
|
||||||
|
*/
|
||||||
|
public static void main(String[] args) {
|
||||||
|
VectorComplex a = new VectorComplex(new NumberComplex(5), new NumberComplex(1), new NumberComplex(1));
|
||||||
|
System.out.println(a.toString());
|
||||||
|
VectorComplex.fill(new NumberComplex(2.), new NumberComplex(2.5)).println();
|
||||||
|
VectorComplex.fill(new NumberComplex(2.), new NumberComplex(8)).println();
|
||||||
|
VectorComplex.fill(new NumberComplex(8.), new NumberComplex(2)).println();
|
||||||
|
VectorComplex.fill(new NumberComplex(2.), new NumberComplex(2), new NumberComplex(8)).println();
|
||||||
|
VectorComplex.fill(new NumberComplex(8.), new NumberComplex(-2), new NumberComplex(2)).toConsoleT();
|
||||||
|
System.out.println("a isNull? : " + a.isZero());
|
||||||
|
System.out.println("a-a isNull? : " + a.minus(a).isZero());
|
||||||
|
}
|
||||||
|
}
|
||||||
12
src/math/number/Number.java
Normal file
12
src/math/number/Number.java
Normal file
@@ -0,0 +1,12 @@
|
|||||||
|
package math.number;
|
||||||
|
|
||||||
|
import thisandthat.WObject;
|
||||||
|
|
||||||
|
public class Number extends WObject {
|
||||||
|
|
||||||
|
public static void main(String[] args) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
377
src/math/number/NumberComplex.java
Normal file
377
src/math/number/NumberComplex.java
Normal file
@@ -0,0 +1,377 @@
|
|||||||
|
package math.number;
|
||||||
|
|
||||||
|
import math.Maths;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Data type for complex number ∈ℂ which defines complex arithmetic and
|
||||||
|
* mathematical functions.
|
||||||
|
* @author Daniel Weschke
|
||||||
|
*/
|
||||||
|
public final class NumberComplex extends Number{
|
||||||
|
|
||||||
|
/**
|
||||||
|
* real part ℜ
|
||||||
|
*/
|
||||||
|
private double ℜ;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* imaginary part ℑ
|
||||||
|
*/
|
||||||
|
private double ℑ;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructs the complex number z = a + bi, a,b=0
|
||||||
|
*/
|
||||||
|
public NumberComplex(){
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructs the complex number z = a + bi, b=0
|
||||||
|
* @param a real part
|
||||||
|
*/
|
||||||
|
public NumberComplex(double a){
|
||||||
|
ℜ = a;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructs the complex number z = ℜ(z) + ℑ(z)i
|
||||||
|
* @param ℜ real part
|
||||||
|
* @param ℑ imaginary part
|
||||||
|
*/
|
||||||
|
public NumberComplex(double ℜ, double ℑ){
|
||||||
|
this.ℜ = ℜ;
|
||||||
|
this.ℑ = ℑ;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructs the complex number z = a + bi
|
||||||
|
* @param z complex number
|
||||||
|
*/
|
||||||
|
public NumberComplex(NumberComplex z){
|
||||||
|
this(z.ℜ(), z.ℑ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructs the complex number z = a + bi
|
||||||
|
* @param z complex number
|
||||||
|
* @return complex number
|
||||||
|
*/
|
||||||
|
public NumberComplex assign(NumberComplex z){
|
||||||
|
ℜ = z.ℜ();
|
||||||
|
ℑ = z.ℑ();
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Real part of this complex number
|
||||||
|
* (the x-coordinate in rectangular coordinates).
|
||||||
|
* @return Re(z) where z is this complex number
|
||||||
|
*/
|
||||||
|
public double ℜ(){
|
||||||
|
return ℜ;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Imaginary part of this complex number
|
||||||
|
* (the y-coordinate in rectangular coordinates).
|
||||||
|
* @return ℑ(z) where z is this complex number
|
||||||
|
*/
|
||||||
|
public double ℑ(){
|
||||||
|
return ℑ;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Addition with real number (doesn't change this complex number).<br />
|
||||||
|
* (a+bi) + c = (a+c)+bi.
|
||||||
|
* @param c real number
|
||||||
|
* @return (a+bi) + c
|
||||||
|
* @see #plus(NumberComplex)
|
||||||
|
* @see #plusAssign(NumberComplex)
|
||||||
|
*/
|
||||||
|
public NumberComplex plus(double c){
|
||||||
|
return new NumberComplex(ℜ()+c,ℑ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Addition with complex number (doesn't change this complex number).<br />
|
||||||
|
* (a+bi) + (c+di) = (a+c)+(b+d)i.
|
||||||
|
* @param z complex number
|
||||||
|
* @return (a+bi) + (c+di)
|
||||||
|
* @see #plus(double)
|
||||||
|
* @see #plusAssign(NumberComplex)
|
||||||
|
*/
|
||||||
|
public NumberComplex plus(NumberComplex z){
|
||||||
|
return new NumberComplex(ℜ()+z.ℜ(),ℑ()+z.ℑ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Addition with complex number (does change this complex number).<br />
|
||||||
|
* (a+bi) + (c+di) = (a+c)+(b+d)i.
|
||||||
|
* @param z complex number
|
||||||
|
* @return y = y + z
|
||||||
|
* @see #plus(double)
|
||||||
|
* @see #plus(NumberComplex)
|
||||||
|
*/
|
||||||
|
public NumberComplex plusAssign(NumberComplex z){
|
||||||
|
ℜ += z.ℜ();
|
||||||
|
ℑ += z.ℑ();
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Subtraction of Complex numbers (doesn't change this Complex number).<br />
|
||||||
|
* (a+bi) - c = (a-c)+bi.
|
||||||
|
* @param c real number
|
||||||
|
* @return (a+bi) - c
|
||||||
|
* @see #minus(NumberComplex)
|
||||||
|
*/
|
||||||
|
public NumberComplex minus(double c){
|
||||||
|
return plus(-c);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Subtraction of Complex numbers (doesn't change this Complex number).<br />
|
||||||
|
* (a+bi) - (c+di) = (a-c)+(b-d)i.
|
||||||
|
* @param z complex number
|
||||||
|
* @return (a+bi) - (c+di)
|
||||||
|
* @see NumberComplex#minus(double)
|
||||||
|
*/
|
||||||
|
public NumberComplex minus(NumberComplex z){
|
||||||
|
return new NumberComplex(ℜ()-z.ℜ(),ℑ()-z.ℑ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Scalar multiplication (doesn't change this Complex number).
|
||||||
|
* @param s scalar
|
||||||
|
* @return s(a+bi)
|
||||||
|
* @see #times(NumberComplex)
|
||||||
|
*/
|
||||||
|
public NumberComplex times(double s){
|
||||||
|
return new NumberComplex(ℜ()*s,ℑ()*s);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Complex multiplication (doesn't change this Complex number).
|
||||||
|
* @param z complex number
|
||||||
|
* @return (a+bi)(c+di) = ac-bd + (ad+bc)i
|
||||||
|
* @see #times(double)
|
||||||
|
*/
|
||||||
|
public NumberComplex times(NumberComplex z){
|
||||||
|
// local r and i is needed because re and im depends on re and im
|
||||||
|
double r = ℜ()*z.ℜ() - ℑ()*z.ℑ();
|
||||||
|
double i = ℜ()*z.ℑ() + ℑ()*z.ℜ();
|
||||||
|
return new NumberComplex(r, i);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Division of Complex numbers (doesn't change this Complex number).<br />
|
||||||
|
* (a+bi)/(c+di) = (ac+bd)/(cc+dd) + (bc-ad)/(cc+dd) i
|
||||||
|
* @param z complex number
|
||||||
|
* @return (a+bi)/(c+di) = (ac+bd)/(cc+dd) + (bc-ad)/(cc+dd) i
|
||||||
|
*/
|
||||||
|
public NumberComplex over(NumberComplex z){
|
||||||
|
return times(z.reciprocal());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return a new complex object whose value is the reciprocal of this
|
||||||
|
*/
|
||||||
|
public NumberComplex reciprocal() {
|
||||||
|
double scale = ℜ()*ℜ() + ℑ()*ℑ();
|
||||||
|
return new NumberComplex(ℜ() / scale, -ℑ() / scale);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Modulus or absolute value or length of this complex number
|
||||||
|
* (the distance from the origin in polar coordinates).
|
||||||
|
* @return |z| where z is this Complex number.
|
||||||
|
*/
|
||||||
|
public double mod(){
|
||||||
|
return Maths.hypot(ℜ(), ℑ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Argument or phase of this Complex number
|
||||||
|
* (the angle in radians with the real/x-axis in polar coordinates).
|
||||||
|
* @return arg(z) in radians where z is this Complex number
|
||||||
|
*/
|
||||||
|
public double arg(){
|
||||||
|
return Maths.atan(ℑ(), ℜ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Argument of this complex number
|
||||||
|
* (the angle ∠ in radians with the real/x-axis in polar coordinates).
|
||||||
|
* @return arg(z) in deg where z is this complex number
|
||||||
|
*/
|
||||||
|
public double argd(){
|
||||||
|
return Maths.atand(ℑ(), ℜ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Complex conjugate of this complex number
|
||||||
|
* (the conjugate of x+i*y is x-i*y).
|
||||||
|
* @return z-bar where z is this complex number.
|
||||||
|
*/
|
||||||
|
public NumberComplex conj() {
|
||||||
|
return new NumberComplex(ℜ(),-ℑ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Complex square root (doesn't change this complex number).
|
||||||
|
* Computes the principal branch of the square root, which
|
||||||
|
* is the value with 0 <= arg < pi.
|
||||||
|
* @return sqrt(z) where z is this Complex number.
|
||||||
|
*/
|
||||||
|
public NumberComplex sqrt(){
|
||||||
|
double r=Math.sqrt(this.mod());
|
||||||
|
double ϑ=this.arg()/2;
|
||||||
|
return new NumberComplex(r*Math.cos(ϑ),r*Math.sin(ϑ));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Complex exponential (doesn't change this Complex number).
|
||||||
|
* @return exp(z) where z is this Complex number.
|
||||||
|
*/
|
||||||
|
public NumberComplex exp() {
|
||||||
|
return new NumberComplex(Math.exp(ℜ())*Math.cos(ℑ()),
|
||||||
|
Math.exp(ℜ())*Math.sin(ℑ()));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Principal branch of the complex logarithm of this complex number
|
||||||
|
* (doesn't change this complex number).
|
||||||
|
* The principal branch is the branch with -π < arg <= π.
|
||||||
|
* @return log(z) where z is this Complex number.
|
||||||
|
*/
|
||||||
|
public NumberComplex log() {
|
||||||
|
return new NumberComplex(Math.log(this.mod()),this.arg());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Cosine of this complex number (doesn't change this complex number).<br />
|
||||||
|
* cos(z) = (e<sup>iz</sup>+e<sup>-iz</sup>)/2.
|
||||||
|
* @return cos(z) where z is this Complex number.
|
||||||
|
*/
|
||||||
|
public NumberComplex cos(){
|
||||||
|
return new NumberComplex(cosh(ℑ())*Math.cos(ℜ()),-sinh(ℑ())*Math.sin(ℜ()));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Sine of this complex number (doesn't change this complex number).<br />
|
||||||
|
* sin(z) = (e<sup>iz</sup>-e<sup>-iz</sup>)/(2i).
|
||||||
|
* @return sin(z) where z is this Complex number.
|
||||||
|
*/
|
||||||
|
public NumberComplex sin() {
|
||||||
|
return new NumberComplex(cosh(ℑ())*Math.sin(ℜ()),sinh(ℑ())*Math.cos(ℜ()));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Tangent of this complex number (doesn't change this complex number).<br />
|
||||||
|
* tan(z) = sin(z)/cos(z).
|
||||||
|
@return tan(z) where z is this Complex number.
|
||||||
|
*/
|
||||||
|
public NumberComplex tan() {
|
||||||
|
return sin().over(cos());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Real cosh function (used to compute complex trig functions)
|
||||||
|
* @param ϑ argument
|
||||||
|
* @return (e<sup>ϑ</sup>+e<sup>-ϑ</sup>)/2
|
||||||
|
*/
|
||||||
|
private double cosh(double ϑ){
|
||||||
|
return (Math.exp(ϑ)+Math.exp(-ϑ))/2;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Hyperbolic cosine of this complex number (doesn't change this complex number).<br />
|
||||||
|
* cosh(z) = (e<sup>z</sup> + e<sup>-z</sup>)/2.
|
||||||
|
* @return cosh(z) where z is this Complex number.
|
||||||
|
*/
|
||||||
|
public NumberComplex cosh() {
|
||||||
|
return new NumberComplex(cosh(ℜ())*Math.cos(ℑ()),sinh(ℜ())*Math.sin(ℑ()));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Real sinh function (used to compute complex trig functions)
|
||||||
|
* @param ϑ argumant
|
||||||
|
* @return (e<sup>ϑ</sup>-e<sup>-ϑ</sup>)/2
|
||||||
|
*/
|
||||||
|
private double sinh(double ϑ){
|
||||||
|
return (Math.exp(ϑ)-Math.exp(-ϑ))/2;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Hyperbolic sine of this complex number (doesn't change this complex number).<br />
|
||||||
|
* sinh(z) = (e<sup>z</sup>-e<sup>-z</sup>)/2.
|
||||||
|
* @return sinh(z) where z is this Complex number.
|
||||||
|
*/
|
||||||
|
public NumberComplex sinh(){
|
||||||
|
return new NumberComplex(sinh(ℜ())*Math.cos(ℑ()),cosh(ℜ())*Math.sin(ℑ()));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Negative of this complex number (chs stands for change sign).
|
||||||
|
* This produces a new Complex number and doesn't change this Complex number.<br />
|
||||||
|
* -(x+i*y) = -x-i*y.
|
||||||
|
* @return -z where z is this Complex number.
|
||||||
|
*/
|
||||||
|
public NumberComplex chs() {
|
||||||
|
return new NumberComplex(-ℜ(),-ℑ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A string representation of the complex object.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public String toString(){
|
||||||
|
if(ℑ() == 0) return ""+ℜ();
|
||||||
|
if(ℜ() == 0) return ℑ()+"i";
|
||||||
|
if(ℑ() > 0) return ""+ℜ()+" + "+ℑ()+"i";
|
||||||
|
if(ℑ() < 0) return ""+ℜ()+" - "+(-ℑ())+"i";
|
||||||
|
else return ℜ()+" + i*"+ℑ(); // shouldn't get here (unless Inf or NaN)
|
||||||
|
}
|
||||||
|
|
||||||
|
public void printRe(){
|
||||||
|
System.out.println("ℜ(z) = "+ℜ());
|
||||||
|
}
|
||||||
|
|
||||||
|
public void printIm(){
|
||||||
|
System.out.println("ℑ(z) = "+ℑ());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param args
|
||||||
|
*/
|
||||||
|
public static void main(String[] args) {
|
||||||
|
NumberComplex cn1 = new NumberComplex(4,1);
|
||||||
|
System.out.println("a = "+cn1);
|
||||||
|
NumberComplex cn2 = new NumberComplex(4,-1);
|
||||||
|
System.out.println("b = "+cn2);
|
||||||
|
NumberComplex cn = cn1.times(cn2);
|
||||||
|
System.out.println("a * b = "+cn);
|
||||||
|
System.out.println("mod(): "+(new NumberComplex(4,3).mod()==5));
|
||||||
|
System.out.println(cn.argd());
|
||||||
|
|
||||||
|
|
||||||
|
NumberComplex a = new NumberComplex(5.0, 6.0);
|
||||||
|
NumberComplex b = new NumberComplex(-3.0, 4.0);
|
||||||
|
|
||||||
|
System.out.println("a = " + a);
|
||||||
|
System.out.println("b = " + b);
|
||||||
|
System.out.println("ℜ(a) = " + a.ℜ());
|
||||||
|
System.out.println("ℑ(a) = " + a.ℑ());
|
||||||
|
System.out.println("b + a = " + b.plus(a));
|
||||||
|
System.out.println("a - b = " + a.minus(b));
|
||||||
|
System.out.println("a * b = " + a.times(b));
|
||||||
|
System.out.println("b * a = " + b.times(a));
|
||||||
|
System.out.println("a / b = " + a.over(b));
|
||||||
|
System.out.println("(a / b) * b = " + a.over(b).times(b));
|
||||||
|
System.out.println("conj(a) = " + a.conj());
|
||||||
|
System.out.println("|a| = " + a.mod());
|
||||||
|
System.out.println("tan(a) = " + a.tan());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
154
src/physics/Nyquist.java
Normal file
154
src/physics/Nyquist.java
Normal file
@@ -0,0 +1,154 @@
|
|||||||
|
package physics;
|
||||||
|
|
||||||
|
import java.awt.event.ActionEvent;
|
||||||
|
import java.awt.event.ActionListener;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
|
||||||
|
import javax.swing.JTextField;
|
||||||
|
|
||||||
|
import math.Maths;
|
||||||
|
import math.equation.RationalPolynomial;
|
||||||
|
import math.equation.RationalPolynomialComplex;
|
||||||
|
import math.matrix.Matrix;
|
||||||
|
import math.matrix.Vector;
|
||||||
|
import stdlib.StdDraw;
|
||||||
|
import awt.Draw;
|
||||||
|
|
||||||
|
public class Nyquist{
|
||||||
|
Draw nyquist = new Draw();
|
||||||
|
static JTextField tf = new JTextField();
|
||||||
|
static Thread plot;
|
||||||
|
static Vector X;
|
||||||
|
static Vector Y;
|
||||||
|
|
||||||
|
public Matrix getNyquist() {
|
||||||
|
RationalPolynomial PT11 = new RationalPolynomial("2; 4 1");
|
||||||
|
RationalPolynomial PT12 = new RationalPolynomial("1; 6 1");
|
||||||
|
// RationalFunction I = new RationalFunction("5; 24 0");
|
||||||
|
RationalPolynomial sys = PT11.times(PT12).times(PT12).times(PT12);
|
||||||
|
tf.setText(sys.a.toStr()+"; "+sys.b.toStr());
|
||||||
|
RationalPolynomialComplex crf = new RationalPolynomialComplex(sys);
|
||||||
|
// doule v = crf.getDivident().getRe().getCoef(0);
|
||||||
|
PT11.setSymbolic("s");
|
||||||
|
PT12.setSymbolic("s");
|
||||||
|
sys.setSymbolic("s");
|
||||||
|
crf.setSymbolic("s");
|
||||||
|
return getNyquist(crf);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Matrix getNyquist(RationalPolynomial sys) {
|
||||||
|
tf.setText(sys.a.toStr()+"; "+sys.b.toStr());
|
||||||
|
RationalPolynomialComplex crf = new RationalPolynomialComplex(sys);
|
||||||
|
return getNyquist(crf);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Matrix getNyquist(RationalPolynomialComplex crf){
|
||||||
|
ArrayList<Double> X = new ArrayList<Double>();
|
||||||
|
ArrayList<Double> Y = new ArrayList<Double>();
|
||||||
|
double omega, abs, angle;
|
||||||
|
double x=0, y=0, t=0;
|
||||||
|
double epsilon = 1;
|
||||||
|
double directionX, directionY;
|
||||||
|
while(epsilon > 0.01){
|
||||||
|
omega = t;
|
||||||
|
abs = crf.mod(omega);
|
||||||
|
angle = crf.argd(omega);
|
||||||
|
directionX = + abs * Maths.cosd(angle) - x;
|
||||||
|
directionY = - abs * Maths.sind(angle) - y;
|
||||||
|
|
||||||
|
// Determine the pointers location
|
||||||
|
x += directionX;
|
||||||
|
y += directionY;
|
||||||
|
t += 0.001;
|
||||||
|
|
||||||
|
X.add(x);
|
||||||
|
Y.add(y);
|
||||||
|
epsilon = Maths.hypot(x, y);
|
||||||
|
}
|
||||||
|
|
||||||
|
// get array
|
||||||
|
Object xa[] = X.toArray();
|
||||||
|
Object ya[] = Y.toArray();
|
||||||
|
int imax = xa.length;
|
||||||
|
double[] xd = new double[imax];
|
||||||
|
double[] yd = new double[imax];
|
||||||
|
// the array
|
||||||
|
for(int i=0; i<imax; i++){
|
||||||
|
xd[i] = ((Double) xa[i]).doubleValue();
|
||||||
|
yd[i] = -((Double) ya[i]).doubleValue();
|
||||||
|
}
|
||||||
|
return new Matrix(xd, yd);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setNyquist(){
|
||||||
|
X = new Nyquist().getNyquist().getN(0);
|
||||||
|
Y = new Nyquist().getNyquist().getN(1);
|
||||||
|
nyquist = new Draw(X,Y);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setNyquist(RationalPolynomial sys){
|
||||||
|
X = new Nyquist().getNyquist(sys).getN(0);
|
||||||
|
Y = new Nyquist().getNyquist(sys).getN(1);
|
||||||
|
nyquist = new Draw(X,Y);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void demo(){
|
||||||
|
setNyquist();
|
||||||
|
contents();
|
||||||
|
animate();
|
||||||
|
nyquist.circle(0, 0, 1);
|
||||||
|
// textLeft(nyquist.scaleRight/2, nyquist.scaleTop-0.1*v, String.format("|G| = %.1f", abs1));
|
||||||
|
// textLeft(right/2, up-0.2*v, String.format(" \u03C9\u2081 = %.3f", omega1));
|
||||||
|
// textLeft(right/2, up-0.3*v, String.format(" φr = %.1f°", angle1+180));
|
||||||
|
// textLeft(right/2, up-0.4*v, String.format(" Ar = %.3f", 1/ar1));
|
||||||
|
// double x0 = abs1*(1-dl) * WMath.cosd(angle1);
|
||||||
|
// double y0 = abs1*(1-dl) * WMath.sind(angle1);
|
||||||
|
// double x1 = abs1*(1+dl) * WMath.cosd(angle1);
|
||||||
|
// double y1 = abs1*(1+dl) * WMath.sind(angle1);
|
||||||
|
// line(ar1, -dl, ar1, dl);
|
||||||
|
// text(ar1, v/25, "Ar\u207B\u00B9");
|
||||||
|
// line(x0, y0, x1, y1);
|
||||||
|
// text((abs1+dt*1.5)*WMath.cosd(angle1), (abs1+dt)*WMath.sind(angle1), "φr");
|
||||||
|
}
|
||||||
|
|
||||||
|
public void contents(){
|
||||||
|
StdDraw.frame.setTitle("Nyquist");
|
||||||
|
nyquist.setScale(-1.5, 2.5, -2.5, 1.5);
|
||||||
|
StdDraw.top = 20;
|
||||||
|
StdDraw.frame.add(tf);
|
||||||
|
tf.setBounds(0, 0, 512, 20);
|
||||||
|
tf.addActionListener(new ActionListener() {
|
||||||
|
@Override
|
||||||
|
public void actionPerformed(ActionEvent arg0) {
|
||||||
|
nyquist.stop(); // ohne diesem bleiben noch einige punkte -> doppel thead?
|
||||||
|
Draw.clear();
|
||||||
|
nyquist.show(1);
|
||||||
|
Draw.setProcess(0);
|
||||||
|
RationalPolynomial sys = new RationalPolynomial(tf.getText().toString());
|
||||||
|
setNyquist(sys);
|
||||||
|
animate();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
public void animate(){
|
||||||
|
if(X==null) demo();
|
||||||
|
nyquist.markX(-1);
|
||||||
|
nyquist.animate();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 2.0 ; 264.0 348.0 80.0 22.0 1.0
|
||||||
|
* 10.0 2.0 1.0 ; 864.0 648.0 180.0 22.0
|
||||||
|
* 2.0 ; 64.0 1.0 1.0
|
||||||
|
* @param args
|
||||||
|
*/
|
||||||
|
public static void main(String[] args) {
|
||||||
|
Nyquist ny = new Nyquist();
|
||||||
|
// ny.setNyquist(new RationalPolynomial("10.0 2.0 1.0 ; 864.0 648.0 180.0 22.0"));
|
||||||
|
// ny.setNyquist(new RationalPolynomial("10.0 2.0 1.0 ; 864.0 648.0 180.0 22.0"));
|
||||||
|
ny.animate();
|
||||||
|
ny.nyquist.cross();
|
||||||
|
System.out.println();
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user