Ho un'applicazione legacy map viewer che utilizza WinForms. È sloooooow. (La velocità era accettabile, ma Google Maps, Google Earth è venuto avanti e gli utenti si sono lasciati viziare. Ora sono autorizzato a effettuare se più veloce :)Offloading trasformazioni di coordinate in GPU
Dopo aver eseguito tutti gli evidenti miglioramenti di velocità (memorizzazione nella cache, esecuzione parallela, non disegno cosa non ha bisogno di essere disegnato, ecc.), il mio profilo mi mostra che il vero punto di soffocamento è la trasformazione delle coordinate quando si convertono i punti dallo spazio della mappa allo spazio dello schermo. Normalmente un codice di conversione è simile al seguente:
public Point MapToScreen(PointF input)
{
// Note that North is negative!
var result = new Point(
(int)((input.X - this.currentView.X) * this.Scale),
(int)((input.Y - this.currentView.Y) * this.Scale));
return result;
}
L'implementazione reale è più complicato. Latitudes/longitues sono rappresentati come numeri interi. Per evitare di perdere la precisione, vengono moltiplicati per 2^20 (~ 1 milione). Ecco come viene rappresentata una coordinata.
public struct Position
{
public const int PrecisionCompensationPower = 20;
public const int PrecisionCompensationScale = 1048576; // 2^20
public readonly int LatitudeInt; // North is negative!
public readonly int LongitudeInt;
}
È importante che i possibili fattori di scala sono esplicitamente tenuti a potenza di 2. Ciò permette di sostituire la moltiplicazione con un Bitshift. Quindi la vera algoritmo simile a questo:
public Point MapToScreen(Position input)
{
Point result = new Point();
result.X = (input.LongitudeInt - this.UpperLeftPosition.LongitudeInt) >>
(Position.PrecisionCompensationPower - this.ZoomLevel);
result.Y = (input.LatitudeInt - this.UpperLeftPosition.LatitudeInt) >>
(Position.PrecisionCompensationPower - this.ZoomLevel);
return result;
}
(UpperLeftPosition representents nell'angolo in alto a sinistra dello schermo nello spazio carta.) Sto pensando ora di scarico questo calcolo alla GPU. Qualcuno può mostrarmi un esempio su come farlo?
Utilizziamo .NET4.0, ma il codice dovrebbe preferibilmente funzionare anche su Windows XP. Inoltre, le librerie sotto GPL non possono essere utilizzate.
+1 per mostrare i limiti teorici. – user256890
Solo per mettere i numeri in prospettiva, qual è la velocità approssimativa di una CPU media a 2 core in FLOP? – user256890
Dipende da ciò che chiamate FLOP. Diciamo che la tua CPU a 2 core ha una velocità di clock di 2 GHz e un FLOP richiede 4 cicli di clock. Potresti fare 2 * 2/4 = 1 GFLOP. Questa è una stima molto approssimativa. –