2012-05-02 6 views
16

अपने आवेदन में मैं CodeDom.Compiler का उपयोग कर source.cs फ़ाइल से किसी अन्य प्रोग्राम संकलन और मैं का उपयोग कर संकलन समय पर कुछ संसाधनों (exe और dll फ़ाइलों) को एम्बेड:एक एम्बेडेड संसाधन को डिस्क पर लिखने के बिना बाइट्स की सरणी के रूप में कैसे पढ़ा जाए?

// .... rest of code 

if (provider.Supports(GeneratorSupport.Resources)) 
{ 
    cp.EmbeddedResources.Add("MyFile.exe"); 
} 
if (provider.Supports(GeneratorSupport.Resources)) 
{ 
    cp.EmbeddedResources.Add("New.dll"); 
} 
// ....rest of code 

संकलित फ़ाइल में, मैं पढ़ने की जरूरत है बाइट्स के सरणी के रूप में एम्बेडेड संसाधन। अब मैं कर रहा हूँ कि नीचे समारोह और उपयोग का उपयोग कर डिस्क के लिए संसाधनों निकाल कर

File.ReadAllBytes("extractedfile.exe"); 
File.ReadAllBytes("extracteddll.dll"); 

मैं इस समारोह का उपयोग कर डिस्क के लिए दो फ़ाइलों को निकालने के बाद ऐसा करते हैं:

public static void ExtractSaveResource(String filename, String location) 
{ 
    // Assembly assembly = Assembly.GetExecutingAssembly(); 
    System.Reflection.Assembly a = System.Reflection.Assembly.GetExecutingAssembly(); 
    // Stream stream = assembly.GetManifestResourceStream("Installer.Properties.mydll.dll"); // or whatever 
    // string my_namespace = a.GetName().Name.ToString(); 
    Stream resFilestream = a.GetManifestResourceStream(filename); 
    if (resFilestream != null) 
    { 
     BinaryReader br = new BinaryReader(resFilestream); 
     FileStream fs = new FileStream(location, FileMode.Create); // say 
     BinaryWriter bw = new BinaryWriter(fs); 
     byte[] ba = new byte[resFilestream.Length]; 
     resFilestream.Read(ba, 0, ba.Length); 
     bw.Write(ba); 
     br.Close(); 
     bw.Close(); 
     resFilestream.Close(); 
    } 
    // this.Close(); 
} 

मैं कैसे कर सकता है वही काम करें (एम्बेडेड संसाधन बाइट्स के सरणी के रूप में प्राप्त करें) लेकिन हार्ड डिस्क पर कुछ भी लिखे बिना?

उत्तर

23

आप वास्तव में पहले से ही एक बाइट सरणी में स्ट्रीम पढ़ रहे हैं, क्यों न केवल वहां रुकें?

public static byte[] ExtractResource(String filename) 
{ 
    System.Reflection.Assembly a = System.Reflection.Assembly.GetExecutingAssembly(); 
    using (Stream resFilestream = a.GetManifestResourceStream(filename)) 
    { 
     if (resFilestream == null) return null; 
     byte[] ba = new byte[resFilestream.Length]; 
     resFilestream.Read(ba, 0, ba.Length); 
     return ba; 
    } 
} 

संपादित करें: एक बेहतर पठन पैटर्न के लिए टिप्पणियां देखें।

+1

मेरा उत्तर अपडेट किया गया, जब आप पहले से ही बाइट सरणी में स्ट्रीम पढ़ रहे हों तो स्मृति स्ट्रीम की आवश्यकता नहीं है। – Rotem

+2

यह सही ढंग से काम नहीं कर सकता है, क्योंकि 'Stream.Read() 'सभी डेटा को एक' रीड()' में वापस नहीं कर सकता है। मुझे यकीन नहीं है कि यह विशिष्ट 'स्ट्रीम' व्यवहार कैसे करता है, लेकिन सुरक्षित पक्ष पर रहने के लिए मैं उसमें 'मेमोरीस्ट्रीम', 'कॉपीटो()' का उपयोग करता हूं और फिर 'ToArray() 'का उपयोग करता हूं। – svick

+0

@svick: आप सही हैं। वैकल्पिक रूप से, कोई इस पृष्ठ पर उदाहरण में वर्णित रीडिंग पैटर्न का उपयोग कर सकता है: http://msdn.microsoft.com/en-us/library/system.io.stream.read.aspx – Rotem

संबंधित मुद्दे