![]() |
|
|||||||
| Newsgroup microsoft.public.de.german.entwickler.dotnet.csharp Forum microsoft.public.de.german.entwickler.dotnet.csharp |
![]() |
|
|
Themen-Optionen | Ansicht |
|
#1
|
|||
|
|||
|
Hallo,
ich habe eine Bitmap aus einer bmp geladen, und bearbeite sie anschließend: Bitmap b2 = b1.Clone() as Bitmap; BitmapData b2data = b2.LockBits(...., PixelFormat.Format24bppRgb) .... b2.UnlockBits(b2data); Anschließend speichere ich sie wieder: b2.Save(filename); Das Problem: Diese Datei kann z.B. von PaintShopPro nicht geladen werden ("keine gültige BMP/DIB/RLE Datei"). Allerdings, von MS Paint kann sie sehr wohl geladen werden. Wenn ich sie dann darin speichern will, werden die Farben auf 2 reduziert. Nur als PNG kann ich sie richtig speichern (in MS Paint). Ich vermute, ich muß die neue Bitmap nochmal umformatieren, oder? Wenn ja, wie? Vielen Dank! Fritz |
|
|
||||
|
||||
|
|
|
#2
|
|||
|
|||
|
Nochmals Hallo,
ich ziehe die Frage zurück. Ich weiß zwar nicht, ob das 100%ig korrekt ist, aber Image.Save(filename, ImageFormat.Bmp) klappt. Gruß, Fritz "Fritz Hilgemann" <Fritzt.Hilgemann*siemens.com> wrote in message news:hd20dm$pah$1*mail1.sbs.de... > Hallo, > > ich habe eine Bitmap aus einer bmp geladen, und bearbeite sie > anschließend: > Bitmap b2 = b1.Clone() as Bitmap; > BitmapData b2data = b2.LockBits(...., PixelFormat.Format24bppRgb) > ... > b2.UnlockBits(b2data); > Anschließend speichere ich sie wieder: > b2.Save(filename); > > Das Problem: Diese Datei kann z.B. von PaintShopPro nicht geladen werden > ("keine gültige BMP/DIB/RLE Datei"). > Allerdings, von MS Paint kann sie sehr wohl geladen werden. Wenn ich sie > dann darin speichern will, werden die Farben auf 2 reduziert. > Nur als PNG kann ich sie richtig speichern (in MS Paint). > > Ich vermute, ich muß die neue Bitmap nochmal umformatieren, oder? Wenn ja, > wie? > > Vielen Dank! > Fritz > |
|
#3
|
|||
|
|||
|
Fritz Hilgemann schrieb:
> ich habe eine Bitmap aus einer bmp geladen, und bearbeite sie anschließend: > Bitmap b2 = b1.Clone() as Bitmap; > BitmapData b2data = b2.LockBits(...., PixelFormat.Format24bppRgb) > ... > b2.UnlockBits(b2data); > Anschließend speichere ich sie wieder: > b2.Save(filename); > > Das Problem: Diese Datei kann z.B. von PaintShopPro nicht geladen werden > ("keine gültige BMP/DIB/RLE Datei"). Wenn Du kein Zielformat angibst, wird die Bitmap als PNG Grafik gespeichert. Siehe: Image.Save Method (String) http://msdn.microsoft.com/en-us/library/ktx83wah.aspx > Allerdings, von MS Paint kann sie sehr wohl geladen werden. PSP lässt sich von der Dateierweiterung in die Irre führen, während MS Paint den Header betrachtet und auf dessen Basis den passenden Encoder verwendet. Thorsten Dörfler -- Microsoft MVP Visual Basic vb-hellfire visual basic faq | vb-hellfire - einfach anders http://vb-faq.de/ | http://www.vb-hellfire.de/ |
|
#4
|
|||
|
|||
|
Fritz Hilgemann schrieb:
> Bitmap b2 = b1.Clone() as Bitmap; Der Safecast ist hier überflüssig und, soweit ich weiß, auch langsamer als ein "richtiger" Cast. Schreibe also besser: Bitmap b2 = (Bitmap)b1.Clone(); Viele Grüße Marvin |
|
#5
|
|||
|
|||
|
Marvin Massih wrote:
> > Bitmap b2 = b1.Clone() as Bitmap; > > Der Safecast ist hier überflüssig und, soweit ich weiß, auch langsamer > als ein "richtiger" Cast. Ich bin mir ziemlich sicher, dass das nicht stimmt. Ein direkter Cast wird über den IL Opcode 'castclass' implementiert -- der Safecast wird über 'isinst' implementiert. Im Erfolgsfall sind beide gleich schnell [1], aber im Fehlerfall ist 'isinst' wesentlich schneller, weil keine Exception geworfen werden muss. > Schreibe also besser: > > Bitmap b2 = (Bitmap)b1.Clone(); Da stimme ich in diesem Kontext allerdings zu. Ich würde den Safecast nur verwenden, wenn ich sinnvolle Entscheidungen auf Basis des Ergebnisses fälle. Code, den man häufigt sieht ist dieser: void DoSomething(Foo foo) { var bar = foo as Bar; if (bar != null) bar.DoSomething(); } In manchen Fällen ist das angemessen (wenn die Operatin wirklich nur für Bars gemacht werden soll), aber in vielen Fällen ist das schlicht falsch, weil man damit lediglich Fehlermaskierung betreibt. Wenn man sicher ist, dass der Cast funktieren muss, sollte man diese Annahme auch im Source Code ausdrücken, also einen direkten Cast verwenden. [1] Unter .NET 1.0/1.1 war 'isinst' noch einen Tacken schneller, aber das Problem ist mittlerweile behoben. -- Immo Landwerth |
|
#6
|
|||
|
|||
|
Hallo Marvin,
>> Bitmap b2 = b1.Clone() as Bitmap; > Der Safecast ist hier überflüssig und, soweit ich > weiß, auch langsamer als ein "richtiger" Cast. > Schreibe also besser: > Bitmap b2 = (Bitmap)b1.Clone(); Nein, "as" ist normal schneller. [CodeProject: Type casting impact over execution performance in C#] http://www.codeproject.com/KB/cs/csharpcasts.aspx Dennoch ist da gleich wieder der "Apfel-Birnen" Vergeichs-Aspekt zu nennen, denn beide tuen letztlich etwas anderes. "as" liefert z.B. keine Exception, sondern null, wenn kein Success. BTW: die reale Zeit dieser Castings liegt bei einem Bruchteil einer Milliardstel Sekunde. Insofern wird oft der semantische und nicht der Performance vorgezogen. [as (C#-Referenz)] http://msdn.microsoft.com/de-de/library/cscsdfbt.aspx ciao Frank -- Dipl.Inf. Frank Dzaebel [MCP/MVP C#] http://Dzaebel.NET |
|
#7
|
|||
|
|||
|
Hallo Immo,
> Im Erfolgsfall sind beide gleich schnell [1], aber im Fehlerfall ist > 'isinst' wesentlich schneller, weil keine Exception geworfen werden > muss. Auch für den Erfolgsfall IMHO, aber vielleicht hast Du was anderes gemeint. Als Beispiel: private void Form1_Load(object sender, EventArgs e) { const int eineMilliarde = 1000000000; Stopwatch sw = Stopwatch.StartNew(); for (int i = 0; i < eineMilliarde; i++) { Form f = (Form)sender; } MessageBox.Show(sw.Elapsed.ToString()); //8,52 Sek sw = Stopwatch.StartNew(); for (int i = 0; i < eineMilliarde; i++) { Form f = sender as Form; } MessageBox.Show(sw.Elapsed.ToString()); //6,14 Sek } >> Schreibe also besser: >> Bitmap b2 = (Bitmap)b1.Clone(); > > Da stimme ich in diesem Kontext allerdings zu. Dazu ist der Kontext IMHO nicht vollständig beschrieben um zuzustimmen, oder nicht. Das Clone kann schiefgehen, und dann möchte man ggf. elegant/angemessen reagieren. In der Praxis hat "as" zum Beispiel vom Schreiben her z.T. eine Ersparnis. Es ist auch z.T. Stil-Frage. > In manchen Fällen ist das angemessen (wenn die Operatin wirklich nur > für Bars gemacht werden soll), aber in vielen Fällen ist das schlicht > falsch, weil man damit lediglich Fehlermaskierung betreibt. ich würde das Thema nicht mit dem Wort "vielen" pauschalisieren, oder eins präferieren, sondern schon sagen, es kommt u.a. zu einem erheblichen Teil auf die Wahrscheinlich des Auftretens an, welches Handling gewählt wird. Andere Dinge können das gesamte Exception-Handling-Konzept ansich sein. BTW: auch Fehlermaskierung ist nur eine "Methode", die nicht pauschal "böse" ist, sondern je nach Szenario viele Vorteile hat. > Wenn man sicher ist, dass der Cast funktieren muss, sollte man diese > Annahme auch im Source Code ausdrücken, also einen direkten Cast > verwenden. ~ja, es ist ~häufig sinnvoll die Ausnahme nach oben zu propagieren, es kommt allerdings hier wieder auf die Wahrscheinlichkeit des Fehlers an .. (Dont use Exception to control flow). ciao Frank -- Dipl.Inf. Frank Dzaebel [MCP/MVP C#] http://Dzaebel.NET |
|
#8
|
|||
|
|||
|
Frank Dzaebel schrieb:
> Nein, "as" ist normal schneller. Oh, das hatte ich dann falsch in Erinnerung, danke. > Dennoch ist da gleich wieder der "Apfel-Birnen" Vergeichs-Aspekt > zu nennen, denn beide tuen letztlich etwas anderes. > "as" liefert z.B. keine Exception, sondern null, wenn kein Success. Ich weiß... > BTW: die reale Zeit dieser Castings liegt bei einem Bruchteil einer > Milliardstel Sekunde. Insofern wird oft der semantische und nicht > der Performance vorgezogen. Ja, mir ging es hier auch vorrangig um die Semantik. Unnötig verwendete as-Casts können einem böse auf die Füße fallen, wenn man irgendwo etwas umstellt und auf einmal NullReferenceExceptions bekommt - da ist eine klare InvalidCastException doch deutlich angenehmer. Gruß Marvin |
|
#9
|
|||
|
|||
|
Hallo Marvin,
schön, dann sind wir einer Meinung. > Unnötig verwendete as-Casts können einem böse auf die Füße fallen, wenn > man irgendwo etwas umstellt und auf einmal NullReferenceExceptions > bekommt - da ist eine klare InvalidCastException doch deutlich angenehmer. Du meinst hier, wenn man den null-Wert bei "as" nicht behandelt, und dann die gecastete Variable später benutzen würde ... ACK. Allerdings implementiert man ja normal diese null-Abfrage, bzw. sollte es. Ansonsten: d'accord. ciao Frank -- Dipl.Inf. Frank Dzaebel [MCP/MVP C#] http://Dzaebel.NET |
|
#10
|
|||
|
|||
|
Hallo Frank,
Frank Dzaebel schrieb: >> Unnötig verwendete as-Casts können einem böse auf die Füße fallen, wenn >> man irgendwo etwas umstellt und auf einmal NullReferenceExceptions >> bekommt - da ist eine klare InvalidCastException doch deutlich >> angenehmer. > > Du meinst hier, wenn man den null-Wert bei "as" nicht behandelt, und > dann die gecastete Variable später benutzen würde ... ACK. > Allerdings implementiert man ja normal diese null-Abfrage, bzw. sollte es. > Ansonsten: d'accord. Ja, ich meinte gerade den Fall, wo man einen as-Cast unnötig verwendet, also einen passenden Typ erwartet und deshalb nicht auf null prüft. Da sollte man besser den "normalen" Cast verwenden, der das auch ausdrückt. Viele Grüße Marvin |
|
|
|
|
![]() |
| Themen-Optionen | |
| Ansicht | |
|
|
Ähnliche Themen
|
||||
| Thema | Erstellt von | Forum | Antworten | Letzter Beitrag |
| Bitmap auf Bitmap kopieren mit anderer Größe im Quickreport! | Paul Sprick | Newsgroup de.comp.lang.delphi.misc | 4 | 12-02-2008 05:58 PM |
| Bitmap to JPG | Marc | Newsgroup microsoft.public.de.german.entwickler.dotnet.csharp | 8 | 04-11-2008 07:05 AM |
| Bitmap clonen! | Marc | Newsgroup microsoft.public.de.german.entwickler.dotnet.csharp | 4 | 04-10-2008 11:57 AM |
| ShieldIcon als Bitmap | Thomas Cebulla | Newsgroup de.comp.lang.delphi.misc | 8 | 02-22-2008 07:46 AM |
| Bitmap aus Ressorcendatei | Norbert Stellberg | Newsgroup de.comp.lang.delphi.misc | 2 | 07-26-2007 07:39 AM |