2016-05-24 6 views
1

Angenommen A ist ein abstrakter Typ, ich habe eine Funktion f{T<:A}(x::Vector{A}). So könnte x Typ Vector{A} oder Vector{B} sein, wobei B <: A. In der Mitte der Funktion möchte ich x zu Vector{A} umwandeln, damit es von einer anderen Funktion konsumiert werden kann, die diese Signatur erfordert.Wie kann Vector {T} (T <: A) am schnellsten an Vector {A} übergeben werden?

Was ist der beste Weg, das zu tun? Im Moment mache ich x = collect(A, x). Gibt es eine Möglichkeit, das Kopieren möglichst zu vermeiden?

Antwort

4

Wenn überhaupt möglich, würde ich nur Ihre zweite Funktionsdefinition als parametrisch wie f ändern. Das Erzwingen dieser Art von Containerstruktur in Methodensignaturen ist ein großer Leistungsfehler, der Ihnen keine Funktionalität bringt ... und sie nur viel schwieriger zu verwenden macht.

Das heißt, der beste Weg, um diese Art von Konvertierung zu machen, wo es egal ist, wenn die Ausgabe Aliasnamen der Eingabe ist mit convert(Vector{A}, x). Dies wird ein No-Op sein, wenn x bereits isa Vector{A}, aber ansonsten wird es wie collect sein. Das ist so gut wie es geht.

Hier ist der Grund: zwei Container von Typen Vector{A} und Vector{B} nicht den gleichen Speicher, wenn A !== B teilen kann, da sie durch die Zuweisung eines nicht B Element in das Array durch die Vector{A}-korrupte Daten im Vector{B} möglich sein würde.

+0

Ich hatte gedacht, nur Bit-Typ würde effizient in einem Array gepackt werden. Oder zumindest unveränderlich mit Feldern, die alle Bit-Typ sind. – colinfang

+0

Sie haben Recht; Ich war nicht genau genug in meiner Sprache. Ich habe nur diesen Teil der Begründung entfernt - die Un-Sicherheit der Operation ist ein guter Grund dafür, warum dies nicht unterstützt wird. –