Ich habe im Laufe der Übungen für 70-536 einen kleinen Taskmanager erstellt, der auch einen Performance-Counter beinhaltet. Da ich auch mit Netzlaufwerken arbeite ist mir aufgefallen, dass wenn ich das Progrmam von der Netzwerkfestplatte aus starte die Berechtigungen für den Performance-Counter fehlen.
In den 70-536-Unterlagen habe ich bei den Sicherheitsthemen nur gefunden, wie die Berechtigungen für aufgerufene Assemblys verändert werden können, diverse Experimente brachten aber keinen Erfolg; ist es möglich dass das Programm sich selbst die Berechtigung gibt (wenn auch mit einer Warnung vom Framework)?
Ansonsten wäre auch eine Möglichkeit zu überprüfen ob die Berechtigung vorliegt und im anderen Fall den Timer nicht zu starten.
Ein weiteres Problem; ich habe für die Prozessorzeit einen Progress-Bar, der aber verhält sich sehr willkürlich, als sei er zu langsam (geht manchmal hoch wenn der Prozessor eine halbe Sekunde vorher ausgelastet war, dann bleibt er weg usw). Der Timer ist ja nur auf 500 ms eingestellt!
Der Quellcode (ist nicht so lang)
namespace netTaskmanager
{//[PerformanceCounterPermission(System.Security.Permissions.SecurityAction.Assert, CategoryName="Prozessor")]
//[PerformanceCounterPermission(System.Security.Permissions.SecurityAction.RequestMinimum, CategoryName="Prozessor")]
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
timer1.Enabled = true;
ListProcesses();
}
private void ListProcesses()
{
listBox1.Items.Clear();
Process[] processes = Process.GetProcesses();
foreach (Process p in processes)
{
StringBuilder s = new StringBuilder();
s.Append(p.ProcessName);
if (!p.Responding)
{
s.Append(" Reagiert nicht");
}
listBox1.Items.Add(s.ToString());
}
}
private void button1_Click(object sender, EventArgs e)
{
if (listBox1.SelectedItem != null)
{
Process[] processes = Process.GetProcessesByName(listBox1.SelectedItem.ToString());
foreach (Process p in processes)
{ p.Kill(); }
ListProcesses();
}
}
private void timer1_Tick(object sender, EventArgs e)
{
label1.Text = performanceCounter1.NextValue().ToString();
progressBar1.Value = (int)performanceCounter1.NextValue();
progressBar1.Invalidate();
}
private void button2_Click(object sender, EventArgs e)
{
Process p = Process.Start("explorer");
ListProcesses();
}
private void button3_Click(object sender, EventArgs e)
{
Process[] processes = Process.GetProcessesByName("explorer");
foreach (Process p in processes)
{ p.Kill(); }
ListProcesses();
}
private void Aktualisieren_Click(object sender, EventArgs e)
{
ListProcesses();
}
private void button4_Click(object sender, EventArgs e)
{
Process[] processes = Process.GetProcesses();
foreach (Process p in processes)
{
if (!p.Responding)
{
p.Kill();
}
}
ListProcesses();
}
}
}
wenn deine combobox den zustand readonly hat, merk dir den wert von SelectedIndex. Wenn dann das ereignis SelectedIndexChanged auftritt, setze den index zurück auf den "gemerkten" wert. das gleiche musst du auch für die eigenschaft Text tun, wenn die ComboBox eingabe von beliebigem text erlaubt.
ist vielleicht nicht die eleganteste lösung, hat aber auf jeden fall den gewünschten effekt.
oder du probierst das hier, wobei das nur ne fixe überlegung ist und möglicherweise nicht funktioniert:
// codebeispiel modifiziert von David_pb
public class ComboBoxEx : ComboBox
{
private bool mReadOnly;
[DefaultValue( false )]
public bool ReadOnly
{
get { return mReadOnly; }
set { mReadOnly = value; }
}
protected override void OnDropDown(EventArgs e)
{
base.OnDropDown(e);
if ( ReadOnly )
RecreateHandle();
}
protected override void OnKeyDown(EventArgs e)
{
if ( ReadOnly )
return;
base.OnKeyDown(e);
}
// evtl. muss man hier auf gleiche weise noch andere key-events überschreiben
}
So sollte es gehen:
//Auf Klassen oder Namespaceebene:
public delegate int MyAction(int a);
//Verwendung:
MyAction b = new MyAction(delegate(int a){return a+a;});
Wenn du weißt, dass es geht musst du nur in der MSDN suchen ...!
Aber wozu LINQ bemühen, wenn es auch mit "Bordmitteln" geht? Spatzen, Kanonen und so ...
Danke, hab die 2. Variante genommen und die Daten mittels DataRow.ItemArray kopiert:
tblPositionen.Rows.Add(row.ItemArray);
So hat es dann funktioniert
die sql abfrage sollte eigendlich wie ne art funktion mit parametern aufgerufen werden aber hab jetzt den fehler entdeckt im dataset habe ich die Insert abfrage falsch generiert
MrCamelcase schrieb:
Im Internet bezeichnen sich viele Dokumente als "Standard" oder "de-facto Standard" und trotzdem wird es immer unterschiedlich gemacht.
Auch wenn es von Microsoft selbst nicht komplett gelebt wird (Viele Köche verderben den Brei; zudem sind diese wohl auch erst im Verlauf der Entwicklung entstanden), halte ich mich im wesentlichen an offizielle Vorgaben, speziell die Richlinien für die Benennung.
cu André
Vermutlich wird es sich dabei um ein spezielles Objekt handeln, welches der Compiler (einer, der optionale Parameter unterstützt) bei nicht übergebenen Parametern einsetzt, damit der Empfänger zwischen null und "nicht übergeben" unterscheiden kann.
MrCamelcase schrieb:
@F98:
bezüglich deines Beispiels auf Seite 4, was machst du mit protected/internal ?
Danke und Gruß
Es findet von der Nomenklatur her keine Unterscheidung statt, ist im Grunde auch nicht wichtig, anhand eines Variablennamens zu sehen, ob private oder protected. Mir fällt auf die Schnelle kein Gegenbeispiel ein (Ich muss weg.).
Das ist schonmal eine gute idee... Nun möchte ich aber zwischen den Interface und den Konkreten Service klassen eine Abstracte Klasse zwischen schachteln.. hab sowas gemacht:
public interface IService<TProvider>
{
}
public interface IProvider<T, U> where T : IService<U>
{
object ProviderInfo();
}
public class ProviderA : IProvider<ServiceA, ProviderA>
{
public object ProviderInfo(){throw new NotImplementedException(); }
}
public class ProviderB : IProvider<ServiceB, ProviderB>
{
public object ProviderInfo() { throw new NotImplementedException(); }
}
public abstract class AbstractService<TProvider,TService> : IService<TProvider>
{
public readonly IProvider<TService, TProvider> /*HIER*/_pro = default(IProvider<TService, TProvider>);
public /*HIER*/AbstractService(IProvider<TService, TProvider> pro)
{
_pro = pro;
}
}
public class ServiceB : AbstractService<ProviderB,ServiceB>
{
public ServiceB(ProviderB Pro)
: base(Pro)
{
}
}
public class ServiceA : AbstractService<ProviderA, ServiceA>
{
public ServiceA(ProviderA Pro)
: base(Pro)
{
}
}
Bei HIER Kommen 2 mal der gleiche Fehler welchen ich nich verstehe:
Fehler 2 Der Typ "TService" kann nicht als Typparameter "T" im generischen Typ oder in der generischen Methode "TagLib.IProvider<T,U>" verwendet werden. Es ist keine Boxing-Konvertierung oder Typparameterkonvertierung von "TService" in "TagLib.IService<TProvider>" vorhanden. C:\Documents and Settings\Operator\My Documents\Visual Studio 2008\Projects\TagLib\TagLib\test.cs 28 56 TagLib
Hallo zusammen,
habe derzeit ein Problem mit einer .Net Anwendung (.Net 3.5, kann aber auch in einer tieferen Version kompiliert werden, falls das hilft) die im Netzwerk laufen muss.
D.h. die Anwendung liegt auf einem Netzwerk-Share und muss von verschiedenen Benutzern aufgerufen werden können.
Die Anwendung schreibt allerdings auch in einige XML Dateien, die selbst auf dem Netzwerkshare liegen.
Das Problem dabei:
Sobald die Anwendung selbst im Netzwerk liegt erhalte ich vom .Net Framework eine Security Exception.
Es ist allerdings nicht möglich diese Sicherheitseinstellungen auf allen Rechnern in der Firma zu ändern.
D.h. ich benötige eine Lösung, welche innerhalb des Programms funktioniert.
Kann man das irgendwo einstellen?
Habe mal den Haken "This is a full trust application" gesetzt, was jedoch keine Verbesserung gebracht hat.
Zur Not würde ich eben eine kleine C/C++ Anwendung schreiben, welche meine .Net Anwendung temporär lokal kopiert und dann ausführt. Eine schöne Lösung ist das aber nicht!
Da muss es doch auch etwas anderes geben, oder?
Vielen Dank für einen guten Tipp
Gruß
GaDgeT