I recently came across the problem that I needed a PWM (i.e. pulse-width modulated rectangular signal) generator block in Simulink with variable frequency and duty cycle inputs. I couldn’t find one in the library, so I wrote one.
The rather simple implementation basically consists of three parts: An integrator block with an external reset input is used to create a sawtooth signal. The sawtooth is then compared to a threshold value given by means of the duty cycle to create a rectangular signal. Lastly that signal is scaled to a standard output range of 0..1.
So, suppose you’re in university, it’s that time of the year again (i.e. exams) and you already have written some of them. Some are still left though and you wonder: How hard can you fail — or: how good do you have to be — in the following exams given that you do not want your mean grade to be worse than a given value.
Linear programming
Say you’re in Germany and the possible grades are [1, 1.3, 1.7, 2, .. 4] (i.e. a closed interval) with 1 being the best grade and 4 being only a minor step to a major fuckup. Given that you’ve already written four exams with the grades 1, 1, 1.3 and 1 and that you do not want to have a mean grade worse than 1.49 in the end (because 1.5 would be rounded to 2 on your diploma), but there still are 9 more exams to write, the question is: Which worst-case grades can you have in the following exams and what would that imply for the others?
This is what’s known to be a linear programming or linear optimization problem, and since the values (here: the number of grades) are constrained to be discrete values, it’s integer programming.
The goal of linear programming is to find the arguments \(x\) of the objective function \(f(x)\) such that \(f(x)\) is maximized, given some constraints on \(x\) . In Matlab, all linear programming functions try to minimize the cost function, so the problem is formulated as
Obviously, maximizing an objective function is the same as minimizing it’s negative, so \(\mathrm{max} \, f(\vec{x}) = -\mathrm{min} \left(\, -f(\vec{x}) \right)\) . In Matlab, these kind of problems can be solved with the linprog function.
Fundstück aus der MATLAB-Doku: Korrelierte normalverteilte Zufallsprozesse. Gegeben seien die Erwartungswerte \(\mu\) der Variablen, sowie deren Kovarianzen \(P\) .
Mittels R = mvnrnd(µ, P, N); können dann N Werte gezogen werden.
Zwei unkorrelierte Prozesse mit \(\mu_1 = E(X_1) = 0\) und \(\mu_2 = E(X_2) = 10\) , sowie Varianzen \(\sigma^2_1 = 1\) und \(\sigma^2_2 = 2\) ließen sich wie folgt erzeugen:
N = 5000;
mu = [0 10];
P = [1 0;
0 2];
r = mvnrnd(mu, P, N);
Der entsprechende Plot ergibt das typische Bild:
plot(r(:,1), r(:, 2), 'r+');
axis square;
Zwei korrelierte Prozesse mit denselben Erwartungswerten und Varianzen, aber negativer Kovarianz ( \(cov(X_1, X_2) = -1\) ) werden analog wie folgt erstellt:
P = [1 -1;
-1 2];
r = mvnrnd(mu, P, N);
Dies liefert die erwartete “schräge” Verteilung.
Januar 21st, 2014 GMT +2 von
Markus
2014-01-21T17:49:25+02:002018-03-4T15:15:39+02:00
· 0 Kommentare
Neugierig und etwas gelangweilt kam ich heute auf die Idee, auszuprobieren, was wohl passieren würde, wenn man die beiden Supersampling-VerfahrenFliptri und Flipquad als Filter eines bestehenden Bildes interpretiert. Resultat des Abends: Wir reden nicht darüber.
Grundlage
Beiden Verfahren liegt zugrunde, dass zur Erzeugung eines Pixels mehrere umgebende (Sub-)Pixel ausgewertet werden, wobei das Muster der Auswertung für anliegende Bildpunkte horizontal und/oder vertikal gespiegelt — geflippt — wird. Die beiden Verfahren unterscheiden sich dabei lediglich hinsichtlich der Anzahl der Samplingpunkte.
Anschaulicher in der Grafik: Jeweils drei Samplingpunkte (rot) ergeben einen Bildpunkt (blau) bei Fliptri; Bei Flipquad sind es vier Samplingpunkte pro Bildpunkt.
Der resultierende Bildpunkt B ist dabei schlichtweg die gewichtete Summe aller Samplingpunkte S:
\begin{align}
B = \frac{1}{N} \sum \limits_{i=1}^N S_i
\end{align}
Implementierung in Matlab
Fliptri
Zu jedem Punkt müssen drei umgebende Pixel aufgenommen werden. Im ungespiegelten Fall liegen diese an den Koordinaten (x-1, y-1), (x, y+1) und (x+1, y). Wie aus der Abbildung zu erkennen ist, müssen die X- und Y-Koordinaten (genauer: Deren Offsets -1, 0 und +1) für jede gerade Zeile gespiegelt werden, was man durch folgenden Kunstgriff erreicht:
function pixel = fliptri(x, y, rgb)
% 1 2 3
% +---+---+---+
% | X | | |
% +---+---+---+
% | | | X |
% +---+---+---+
% | | X | |
% +---+---+---+
coords = [ -1 0 +1; % X
-1 +1 0]; % Y
N = length(coords);
% Flip
sgn_x = (-1)^x;
sgn_y = (-1)^y;
% Sample
for s=1:N
sample(s, 1:3) = rgb( ...
x+coords(1,s)*sgn_x, ...
y+coords(2,s)*sgn_y, ...
1:3);
end
% Combine
pixel = sum(sample) / N;
end
Zuletzt muss das Bild noch geladen und gefiltert werden. (Da die Größe des gedachten Filterkernels der Größe drei entspricht, müssen die Start- und Endindizes jeweils um den Wert 1 reduziert werden.)
% Load the image
rgb = imread('aliased.png');
% Sample the image
imagesize = size(rgb);
width = imagesize(1);
height = imagesize(2);
rgb_sampled = uint8(zeros(imagesize));
for y=2:height-1
for x=2:width-1
rgb_sampled(x, y, 1:3) = fliptri(x, y, rgb);
end
end
Flipquad
Analog zum Fliptri funktioniert der Flipquad-Algorithmus, allerdings ist die Offsetkorrektur hier vom Wert zwei, und es werden vier, statt drei Werten verarbeitet:
function pixel = flipquad(x, y, rgb)
% 1 2 3 4 5
% +---+---+---+---+---+
% | | X | | | |
% +---+---+---+---+---+
% | | | | | X |
% +---+---+---+---+---+
% | | | | | |
% +---+---+---+---+---+
% | X | | | | |
% +---+---+---+---+---+
% | | | | X | |
% +---+---+---+---+---+
coords = [ -2 -1 +1 +2; % X
-1 +2 -2 +1]; % Y
N = length(coords);
% Flip
sgn_x = (-1)^x;
sgn_y = (-1)^y;
% Sample
sample = zeros(3,3);
for s=1:N
sample(s, 1:3) = rgb( x+coords(1,s)*sgn_x, ...
y+coords(2,s)*sgn_y, ...
1:3);
end
% Combine
pixel = sum(sample) / N;
end
Der Rest funktioniert wie gehabt.
Das Ergebnis
Ernüchternd scheiße.
Originalbild
Fliptri-gefiltertes Bild
Flipquad-gefiltertes Bild
Und das war das.
Wie ich eingangs bereits erwähnte: … — aber wenigstens war man dabei. Prost.
November 4th, 2011 GMT +2 von
Markus
2011-11-4T03:58:08+02:002018-03-4T14:44:01+02:00
· 0 Kommentare