Login Login
MORE

WIDGETS

Widgets

Recent changes
Wanted articles
Who is online?
Article tools

CSharp:Tips programmazione libreria

From Aino Wiki

Jump to: navigation, search

Stringhe

Conversioni

Es 1

Conversione da una data DateTime in stringa formattata con ToString(":
string text = dateTime.ToString("MM/dd/yyyy HH:mm:ss.fff", CultureInfo.InvariantCulture);
string text2 = dateTime.ToString("dd/MM/yyyy HH:mm:ss.fff");

Es 2

In alternativa alla precedente:
dto = DateTimeOffset.ParseExact(na.localtime.GetValue(), "o", System.Globalization.CultureInfo.InvariantCulture);
Che produrrà il seguente:
?

Ricerche

IndexOf case insensitive

La IndexOf() (indexof) di default è case sensitive, per usarla indipendente da maiuscole minuscole ecco come:
string strCercare = "sotto la panca la capra crepa";
int index = strCercare.IndexOf("la", StringComparison.CurrentCultureIgnoreCase);
Usando StringComparison.CurrentCultureIgnoreCase si effettua una ricerca caseinsensitive.

Ricordo che Indexof restituisce -1 nel caso non trovi il pattern di ricerca altrimenti la posizione nella stringa di ricerca in base 0.

Intersezione

Cercare una porzione stringa comune ad un'altra oppure dati due array di stringhe trovare un array di quelle comuni.
Segue esempio per trovare path comune:

Es. 1
        private static string FindCommonPath(string pathA, string pathB)
        {
            // Supponiamo che nel path si usino solo '/'
            string commonPath = string.Empty;
            try
            {
                if (string.IsNullOrEmpty(pathA) || string.IsNullOrEmpty(pathB))
                {
                    return pathA + pathB;
                }
 
                string[] arrPathA = pathA.Split('/');
                string[] arrPathB = pathB.Split('/');
                int i = 0;
                if (arrPathA.Length > arrPathA.Length)
                {
                    foreach (string itemPath in arrPathA)
                    {
                        if (arrPathB.Length > i
                            && itemPath == arrPathB[i])
                        {
                            commonPath += itemPath + "/";
                        }
                        else
                        {
                            break;
                        }
                        i++;
                    }
                }
                else
                {
                    foreach (string itemPath in arrPathB)
                    {
                        if (arrPathA.Length > i
                            && itemPath == arrPathA[i])
                        {
                            commonPath += itemPath + "/";
                        }
                        else
                        {
                            break;
                        }
                        i++;
                    }
                }
                commonPath = commonPath.Substring(0, commonPath.Length - 1); // Toglie l'ultimo '/'
            }
            catch (Exception ex)
            {
                LoggerMain.Error("Ex.: {0}\r\n\r\n{1}", ex.Message, ex.StackTrace);
            }
            return commonPath;
        }
Es. 2

Dati due array di stringhe trovare un array di quelle comuni Da stackoverflow Date le seguenti:

string[] array1 = { "Red", "blue", "green", "black" };
string[] array2 = { "BlUe", "yellow", "black" };

Trovare come risultato:

string[] result = { "blue", "black" } or { "BlUe", "black" };
var results = array1.Intersect(array2, StringComparer.OrdinalIgnoreCase);

Performance

Nella verifica di una uguaglianza preferisco:
if (string.Equals(v.dataType, 
                  Enums.ShipValuesDataTypes.Wind_speed.ToString(), 
                  StringComparison.OrdinalIgnoreCase))
// ok uguaglianza soddisfatta

Conteggio

Per contare il numero di occorrenze di una sottoStringa in una stringa usando le regular Expression (espressione regolare):

using System.Text.RegularExpressions;
//...
int quanteVolte = Regex.Matches(strCSVAttributeList, "preservativo=").Count;

Split

Ottimi esempi: dotnetperls

es. basic

da Microsoft:
using System;
 
public class SplitTest {
    public static void Main() {
 
        string words = "This is a list of words, with: a bit of punctuation" +
                       "\tand a tab character.";
 
        string [] split = words.Split(new Char [] {' ', ',', '.', ':', '\t' });
 
        foreach (string s in split) {
 
            if (s.Trim() != "")
                Console.WriteLine(s);
        }
    }
}
Output
// The example displays the following output to the console:
//       This
//       is
//       a
//       list
//       of
//       words
//       with
//       a
//       bit
//       of
//       punctuation
//       and
//       a
//       tab
//       character

Split con pattern string, options

C'è la possibilità di indicare opzioni, il seguente es. splitta con stringhe:
      string source = "[stop]ONE[stop][stop]TWO[stop][stop][stop]THREE[stop][stop]";
      string[] stringSeparators = new string[] {"[stop]"};
      string[] result;
      // Split a string delimited by another string and return all elements.
      result = source.Split(stringSeparators, StringSplitOptions.None);
      Console.WriteLine("Result including all elements ({0} elements):", 
                        result.Length);
      Console.Write("   ");
      foreach (string s in result)
      {
         Console.Write("'{0}' ", String.IsNullOrEmpty(s) ? "<>" : s);                   
      }
      Console.WriteLine();
      Console.WriteLine();
Con regularExpression

Usando Regular expression (da MSDN):

using System;
using System.Text.RegularExpressions;
 
public class Example
{
   public static void Main()
   {
      string input = "plum--pear";
      string pattern = "-";            // Split on hyphens
 
      string[] substrings = Regex.Split(input, pattern);
      foreach (string match in substrings)
      {
         Console.WriteLine("'{0}'", match);
      }
   }
}
// The method displays the following output:
//    'plum'
//    ''
//    'pear'

Comparazione

Ordinamento

Segue esempio (da Dot net perls) per verificare quale stringa precede una data. Comparazione tra stringhe per effettuare un ordinamento alfabetico o per determinare l'ultima o la prima di un elenco.
using System;
 
class Program
{
    static void Main()
    {
	string a = "a"; // 1
	string b = "b"; // 2
 
	int c = string.Compare(a, b);
	Console.WriteLine(c);
 
	c = string.CompareOrdinal(b, a);
	Console.WriteLine(c);
 
	c = a.CompareTo(b);
	Console.WriteLine(c);
 
	c = b.CompareTo(a);
	Console.WriteLine(c);
    }
}

Tabella informativa con output prodotto:

String A: First alphabetically
String B: Second alphabetically

Compare(A, B): -1
Compare(B, A):  1

Compare(A, A):  0
Compare(B, B):  0

Nr occorrenze stringa in stringa

Metodo diretto

Esempio copiato da DotNetPerls:
public static int CountStringOccurrences(string text, string pattern)
{
	// Loop through all instances of the string 'text'.
	int count = 0;
	int i = 0;
	while ((i = text.IndexOf(pattern, i)) != -1)
	{
		i += pattern.Length;
		count++;
	}
	return count;
}

Con regular expression=

using System.Text.RegularExpressions;
...
if (Regex.Matches(strOut, imoNumber).Count == 2)
{
     // Esegui azioni
}

Date

Valorizzazioni

Valorizzare una data da una stringa o definirla da una costante:

DateTime data = new DateTime(2002,12,20);

Valorizzare con l'orario UTC (dall'orario in italia togliendo 2 ore):

DateTime data = DateTime.UtcNow;

Parti della data

int giorno = DateTime.Now.Day;
int mese = DateTime.Now.Month;
int anno = DateTime.Now.Year;

Traduzione

Trasformare una data per visualizzarne il testo in lettere:

using System.ComponentModel;
using System.Globalization;
 
//...
CultureInfo ci = new CultureInfo("it-IT");
Console.WriteLine(DateTime.Now.ToString("D", ci));
Console.WriteLine(DateTime.Now.ToString("M", ci));
Console.WriteLine(DateTime.Now.ToString("MMMM", ci));
Console.WriteLine(String.Format("{0:MMMM}", DateTime.Now));

Produrrà:

martedì 7 febbraio 2017
7 febbraio
fabbraio
February

Testo del mese corrente in Italiano:

string mese = string.empty;
string[] mesiInItaliano = 
            { "Gennaio", "Febbraio", "Marzo", "Aprile", "Maggio", "Giugno",
               "Luglio", "Agosto", "Settembre", "Ottobre", "Novembre", "Dicembre"};
 
mese = mesiInItaliano[DateTime.Now.Month - 1]; // in base zero
Console.WriteLine(mese);

Operazioni

Sottrarre aggiungere ad una data

Nel seguente si tolgono 6 mesi alla data di oggi. rdtpOrderDateFrom è un controllo datePicker.

rdtpOrderDateFrom.SelectedDate = Convert.ToDateTime(DateTime.Today.AddMonths(-6));

Differenza tra due date in minuti

Affinchè la differenza sia positiva seguire l'esempio in base alla naming data.

if (DataPiuRECENTE.Value.Subtract(DataVECCHIA).TotalMinutes < minutesHysteresisRange) 
{
     continue; // L'allarme non rientra!
}

Comparazioni

using System;
 
public class Program
{
	public static void Main()
	{
		DateTime draftUpdated = DateTime.UtcNow;
		DateTime sourceDate = DateTime.UtcNow.AddMinutes(-1);
 
		if (draftUpdated > sourceDate)
		{
			Console.Write("Nuova data aggiornata [nuova='{0}' > sorgente='{1}']", draftUpdated, sourceDate);
		}
		else
		{
			Console.Write("Nuova data NON aggiornata [nuova='{0}' < sorgente='{1}']", draftUpdated, sourceDate);
		}
	}
}

Risultato:

Nuova data aggiornata [nuova='8/27/2015 8:35:33 AM' > sorgente='8/27/2015 8:34:33 AM']

Conversioni

Da DateTime a SQLDateTime

Ecco due esempi di come trasformare una data da C# in stringa da passare ad una query in SQL Server:

DateTime myDateTime = DateTime.Now;
string sqlFormattedDate = myDateTime.ToString("yyyy-MM-dd HH:mm:ss");
Oppure il seguente metodo empirico direttamente nella stringa query SQL:
string strQrySQL_lastUpdateUTC_Processed = lastUpdateUTC_Processed == null //yyyy-mm-dd hh:mm:ss.mmm
          ? string.Empty
          : string.Format("{0}-{1}-{2} {3}:{4}:{5}.{6}", lastUpdateUTC_Processed.Value.Year,
                                                         lastUpdateUTC_Processed.Value.Month,
                                                         lastUpdateUTC_Processed.Value.Day,
                                                         lastUpdateUTC_Processed.Value.Hour,
                                                         lastUpdateUTC_Processed.Value.Minute,
                                                         lastUpdateUTC_Processed.Value.Second,
                                                         lastUpdateUTC_Processed.Value.Millisecond
                                     ); 
// etc....
string strQrySQL = string.Format(
@"DECLARE @DateFrom AS DateTime = DATEADD(MINUTE, -30, GetUTCDate()),
          @LastUpdateUTC_Processed AS DateTime = CONVERT(datetime, '{0}', 121); 
", strQrySQL_lastUpdateUTC_Processed );

DataTable

Ricerche Verifiche

Per verificare se una colonna appartiene ad un DataTable ovvero è presente un DataColumn nel DataRow con questo nome:

if (dr.Table.Columns.Contains("source")) // Questo non fa scattare eccezione ma NON VA BENE!!!
{
	result.Source = dr["source"] as string;
}

Filtri

Occorre usare un DataView su cui impostare il filtro e poi passare il DataView come DataSource di un BindingSource

FrmPopUpShipInfo popUp = new FrmPopUpShipInfo();
popUp.Logger4Popup = m_loggerForm;
popUp.ShipFullCode = shipFullCode;
 
popUp.ShipCode = shipCode;
popUp.CompanyCode = companyCode;
 
DataView dvSourceOneShip = new DataView(m_DtAllShipHelp);
DataView dvSourceAllShip = new DataView(m_DtAllShipHelp);
 
dvSourceOneShip.RowFilter = string.Format("key = '{0}'", shipFullCode);
dvSourceAllShip.RowFilter = string.Format("CompanyCode = '{0}'", companyCode);
 
popUp.BindingSrcOneShip.DataSource = dvSourceOneShip;
popUp.BindingSrcAllShip.DataSource = dvSourceAllShip;
 
popUp.ShowDialog();

Accesso alle risorse WEB

Query string

Per ottenere i parametri usando LinQ (preleva parametro 'ships'):

var qs = Request.GetQueryNameValuePairs().ToDictionary(k => k.Key,
                                                                k => k.Value,
                                                                StringComparer.OrdinalIgnoreCase);
string ships = qs["ships"];
string[] shipCodes = ships.Split(';');

Varie

Generare una stringa chiave

Come per le chiavi di attivazione Windows, l'istruzione è Guid
    Guid g = Guid.NewGuid();
    string GuidString = Convert.ToBase64String(g.ToByteArray());
    GuidString = GuidString.Replace("=","");
    GuidString = GuidString.Replace("+","");

Per assegnare un valore NULL ad una variabile Guid:

    Guid g = Guid.NewGuid();
    g = Guid.Empty; // Assegnazione valore VUOTO\Null

Ottenere il nome del Metodo corrente

Da stackOverflow:
using System.Diagnostics;
...
StackTrace st = new StackTrace ();
StackFrame sf = st.GetFrame (0);
 
MethodBase metodoCorrente = sf.GetMethod ();
string nomeDelMetodoCorrente = metodoCorrente.Name;
StackTrace e StackFrame richiedono la using: using System.Diagnostics;

Se invece si vuol fare un metodo di helper:
using System.Diagnostics;

using System.Runtime.CompilerServices; ... [MethodImpl(MethodImplOptions.NoInlining)] public string GetCurrentMethod () {

   StackTrace st = new StackTrace ();
   StackFrame sf = st.GetFrame (1);

 

   return sf.GetMethod().Name;
}
Attenzione, l'attributo del metodo di helper [MethodImpl ..] richiede la using: using System.Runtime.CompilerServices;

File System

Ricerche

Files

Nel caso si voglia acquisire un file ASCII vedere qui File ASCII.

private void LblEventStop_Click(object sender, EventArgs e)
{
	string strMsgOutput = string.Empty;
	int nrUsers = 0;
 
	try
	{
		string[] filePaths = Directory.GetFiles(Model.Configuration.PathDataUserConnected, "*.txt");                
		foreach (string fileNameWithPath in filePaths)
		{
				nrUsers++;
				strMsgOutput += string.Format("Utente: {0}\r\n", fileNameWithPath.Replace("_", "\\"));           
		}
		strMsgOutput = string.Format("Found {0} users:\r\n{1}", nrUsers, strMsgOutput);
		MessageBox.Show(string.Format("{0}", strMsgOutput), string.Format("LblEventStop_Click"),
						MessageBoxButtons.OK, MessageBoxIcon.Information);
	}
	catch (Exception ex)
	{
		Cursor.Current = Cursors.Default;
		m_loggerForm.Error("Ex.: '{0}'\r\n\r\n{1}", ex.Message, ex.StackTrace);
	}
}

Directories

Routine di Helper che acquisisce il contenuto dell'intera cartella indicata:
using System.IO;
//...
public static DirectoryInfo[] GetTopDirectoryListUpperToLow(string topPath)
{
	DirectoryInfo diRoot = new DirectoryInfo(topPath);
	DirectoryInfo[] arrDIList = diRoot.GetDirectories("*", SearchOption.TopDirectoryOnly);
 
	Array.Sort<DirectoryInfo>(arrDIList, new Comparison<DirectoryInfo>(CompareDirsUpperToLow));
 
	return arrDIList;
}

Uso della routine precedente:

	//...
	exeFileName = currService.ExeFileName;
	cfgFileName = string.Format("{0}.config", exeFileName);
 
	DirectoryInfo[] arrDIList = FileHelper.GetTopDirectoryListUpperToLow(srvInstanceDestinationPath);
	string currentDirectoryPath = string.Empty;
	foreach (DirectoryInfo di in arrDIList)
	{
		currentDirectoryPath = di.FullName;
		// Filtro necessario perché alcune navi hanno vecchie cfg, la discriminante è il punto nel nome della cartella
		// si usa un trucco per verificare l'ultima cartella --> Path.GetFileName(
		// che a dispetto del nome controlla l'ultima cartella
		if (Path.GetFileName(currentDirectoryPath).IndexOf('.') > 0 
			&& File.Exists(string.Format("{0}\\{1}", currentDirectoryPath,cfgFileName)))
		{
			pathLastCfgFile = string.Format("{0}\\{1}", currentDirectoryPath, cfgFileName);
			break;
		}
	}

Percorsi / Path

Percorso dell'applicazione

Per avere il percorso completo (directory) dell'applicazione, application path, (ad es un servizio, un assembly) quindi dov'è il file eseguibile:
    string directoryTemplateFiles = AppDomain.CurrentDomain.BaseDirectory;

Altra soluzione più pesante usando la reflection:

    string directoryTemplateFiles = System.Reflection.Assembly.GetEntryAssembly().Location;

Ultima directory di un Path

DirectoryInfo[] arrDIList = FileHelper.GetTopDirectoryListUpperToLow(srvInstanceDestinationPath);
string currentDirectoryPath = string.Empty;
foreach (DirectoryInfo di in arrDIList)
{
	currentDirectoryPath = di.FullName;
	// Filtro necessario perché alcune navi hanno vecchie cfg, la discriminante è il punto nel nome della cartella
	// si usa un trucco per verificare l'ultima cartella --> Path.GetFileName(
	// che a dispetto del nome controlla l'ultima cartella
	if (Path.GetFileName(currentDirectoryPath).IndexOf('.') > 0 
		&& File.Exists(string.Format("{0}\\{1}", currentDirectoryPath,cfgFileName)))
	{
		pathLastCfgFile = string.Format("{0}\\{1}", currentDirectoryPath, cfgFileName);
		break;
	}
}

Come stabilire se un path è un file o directory

Soluzione presa da Stackoverflow
// get the file attributes for file or directory
FileAttributes attr = File.GetAttributes(@"c:\Temp");
 
//detect whether its a directory or file
if ((attr & FileAttributes.Directory) == FileAttributes.Directory)
    MessageBox.Show("Its a directory");
else
    MessageBox.Show("Its a file");

Usando il framework 4.0:

// get the file attributes for file or directory
FileAttributes attr = File.GetAttributes(@"c:\Temp");
 
if (attr.HasFlag(FileAttributes.Directory))
    MessageBox.Show("Its a directory");
else
    MessageBox.Show("Its a file");

Esecuzione di un eseguibile

Si usa Process.Start, ecco un primo semplice esempio:

using System;
using System.Diagnostics;
using System.Threading;
 
namespace RunVS7Resharper
{
    class Program
    {
        static void Main(string[] args)
        {
            string strPathFirst = string.Empty;
            string strPathTwo = string.Empty;
            string strAppFirst = string.Empty;
            string strAppTwo = string.Empty;
            try
            {
                //Process.Start("notepad", "readme.txt");
                strPathFirst = @"D:\Scaricati\SW\Resharper\64Bit";
                strPathTwo = @"C:\Program Files (x86)\Microsoft Visual Studio\2017\Enterprise\Common7\IDE";
                strAppFirst = "dvt-jb_licsrv.amd64.exe";
                strAppTwo = "devenv.exe";
 
                //StartSimple($@"{strPathFirst}\{strAppFirst}", $@"{strPathTwo}\{strAppTwo}");
                StartMore($@"{strPathFirst}\{strAppFirst}", $@"{strPathTwo}\{strAppTwo}");
            }
            catch (Exception e)
            {
                Console.WriteLine(e);
            }
            Console.ReadLine();
        }
        private static void StartSimple(string fullPathFirst, string fullPathTwo)
        {
            try
            {
                Process.Start(fullPathFirst);
                Thread.Sleep(500);
                Process.Start(fullPathTwo);
            }
            catch (Exception e)
            {
                Console.WriteLine(e);
                throw;
            }
        }
 
        private static void StartMore(string fullPathFirst, string fullPathTwo)
        {
            ProcessStartInfo startInfo = new ProcessStartInfo();
            try
            {
                startInfo.CreateNoWindow = false;
                startInfo.UseShellExecute = false;
                startInfo.FileName = fullPathFirst;
                startInfo.WindowStyle = ProcessWindowStyle.Hidden;
                //startInfo.Arguments = "-f j -o \"" + ex1 + "\" -z 1.0 -s y " + ex2;
 
                Process.Start(startInfo);
 
                Thread.Sleep(500);
                startInfo.FileName = fullPathTwo;
                Process.Start(startInfo);
 
                // Per attendere l'esecuzione:
                /*
                 // Start the process with the info we specified.
                 // Call WaitForExit and then the using statement will close.
                 using (Process exeProcess = Process.Start(startInfo))
                 {
                    exeProcess.WaitForExit();
                 }
                 */
            }
            catch (Exception e)
            {
                Console.WriteLine(e);
                throw;
            }
        }
 
    }
}

Query - operazioni sul DB

Effettuare una query con più di un resultset (più di un insieme di dati) da convogliare in due dataTable.
ATTENZIONE lo stesso risultato si può ottenere con i DataReader.

SELECT *
FROM TabellaA
WHERE 1=1;
 
SELECT *
FROM TabellaB
WHERE 1=1;

Quindi col codice C# così fatto raccoglieremo il risultato in due dataTable prendendole con la posizione sul DataSet usato mediante la Fill() del DataAdapter. Notare che le due query di sopra son separate dal ; !

string connetionString = "Data Source=ServerName;Initial Catalog=DatabaseName;User ID=UserName;Password=Password";
 
string qrySQL = 
@"SELECT *
FROM TabellaA
WHERE 1=1;
SELECT *
FROM TabellaB
WHERE 1=1;";
 
DataTable dtA = new DataTable();
DataTable dtB = new DataTable();
 
SqlConnection cnn = new SqlConnection(connetionString));
DataSet ds = new DataSet();
 
try
{
	SqlCommand sqlCmd = new SqlCommand(qrySQL, cnn);
	sqlcmd.CommandType = CommandType.Text;
 
	SqlDataAdapter da = new SqlDataAdapter(sqlCmd));
	cnn.Open();
	da.Fill(ds);
 
	if (ds.Count == 2)
	{
		dtA = ds[0]; // Risultato finale contenente la tabella: 	TabellaA !!!
		dtB = ds[1]; // Risultato finale contenente la tabella: 	TabellaB !!!
	}
}
catch (Exception ex)
{
      logger.Err("{0}", ex.message); // Suppongo ci sia un logger ad es quello di NLOG!
}
finally
{
    if (cnn != null
	&& cnn.State == ConnectionState.Open)) // Non do per scontato che la connessione si sia aperta
	{
		cnn.Close();
	}
}

Ora non ricordo bene ma magari alle due tabelle ci si può accedere col nome anziché con la posizione.

Sistema

Utente corrente

Per ottenere lo user corrente di windows che stà eseguendo l'applicazione:
private bool WelcomNewUser()
        {
            bool ok = true;
            string currentUserName = string.Empty;
            string fullPath  =string.Empty;
            string text = string.Empty; 
            string strMsgError = string.Empty;
            try
            {
                Cursor.Current = Cursors.WaitCursor;
                currentUserName = System.Security.Principal.WindowsIdentity.GetCurrent().Name.Replace("\\", "_");
 
                fullPath = string.Format("{0}//{1}{2}", Model.Configuration.PathDataUserConnected, currentUserName, ".txt");
                text = string.Format("From {0}", DateTime.UtcNow.ToString("dd/MM/yyyy HH:mm:ss.fff"));
                strMsgError = string.Empty;
 
                if (!Directory.Exists(Path.GetDirectoryName(fullPath)))
                {
                    Directory.CreateDirectory(Path.GetDirectoryName(fullPath));
                }
 
                FileHelper.WriteToTextFile(fullPath, text, out strMsgError);
 
                m_loggerForm.Debug("Created welcome file '{0}'\r\nError ? '{1}'", fullPath, strMsgError);
            }
            catch (Exception ex)
            {
                Cursor.Current = Cursors.Default;
                m_loggerForm.Error("Ex.: '{0}'\r\n\r\n{1}", ex.Message, ex.StackTrace);
                ok = false;
            }
            finally
            {
                Cursor.Current = Cursors.Default;
            }
            return ok;
        }
 
        private bool ByeByeUser(string whyExit)
        {
            bool ok = true;
            string currentUserName = string.Empty;
            string fullPath = string.Empty;
            string text = string.Empty;
            string strMsgError = string.Empty;
 
            try
            {
                Cursor.Current = Cursors.WaitCursor;
                currentUserName = System.Security.Principal.WindowsIdentity.GetCurrent().Name.Replace("\\", "_");
                fullPath = string.Format("{0}//{1}{2}", Model.Configuration.PathDataUserConnected, currentUserName, ".txt");
 
                File.Delete(fullPath);
                m_loggerForm.Debug("Welcome file '{0}' deleted.\r\n{1}", fullPath, whyExit);
            }
            catch (Exception ex)
            {
                Cursor.Current = Cursors.Default;
                m_loggerForm.Error("Ex.: '{0}'\r\n\r\n{1}", ex.Message, ex.StackTrace);
                ok = false;
            }
            finally
            {
                Cursor.Current = Cursors.Default;
            }
            return ok;
        }

Nome macchina

Per avere il nome della macchina su cui sta funzionando l'eseguibile ecco come fare:

        private void DeleteLogFile()
        {
            try
            {
                bool esecuzioneDiDebug = false;
#if DEBUG
                esecuzioneDiDebug = true;
#endif
                if (esecuzioneDiDebug
                   && System.Environment.MachineName == "KTB179") // <----- !!!
                {
                    File.Delete("D:/KT/Logs/KTXmlDataCollector/KTCostaXmlDataCollector.log");
                }
            }
            catch (Exception)
            {
            }
        }

Registro di sistema

Scrivere e leggere nel registro per rendere disponibili precedenti impostazioni. (Si può usare RegEdit per visualizzarle e verificarle).
Si usa la classe RegistryKey del namespace Microsoft.Win32
Segue elenco metodi con relativo scopo (preso da StackOverflow):

GetValue       //to get value of a key
SetValue       //to set value to a key
DeleteValue    //to delete value of a key
OpenSubKey     //to read value of a subkey (read-only)
CreateSubKey   //to create new or edit value to a subkey
DeleteSubKey   //to delete a subkey
GetValueKind   //to retrieve the datatype of registry key

Scrivere

RegistryKey key = Registry.LocalMachine.OpenSubKey("Software",true);
 
key.CreateSubKey("AppName");
key = key.OpenSubKey("AppName", true);
 
 
key.CreateSubKey("AppVersion");
key = key.OpenSubKey("AppVersion", true);
 
key.SetValue("yourkey", "yourvalue");

Leggere

Esempio preso da codeproject In input il nome della chiave ed in output il valore:
public string Read(string KeyName)
{
    // Opening the registry key
    RegistryKey rk = baseRegistryKey ;
    // Open a subKey as read-only
    RegistryKey sk1 = rk.OpenSubKey(subKey);
    // If the RegistrySubKey doesn't exist -> (null)
    if (sk1 == null)
    {
        return null;
    }
    else
    {
        try 
        {
            // If the RegistryKey exists I get its value
            // or null is returned.
            return (string)sk1.GetValue(KeyName.ToUpper());
        }
        catch (Exception e)
        {
            ShowErrorMessage(e, "Reading registry " + KeyName.ToUpper());
            return null;
        }
    }
}
Esempio d'uso:
myRegistry.Read("MY_KEY");

Se MY_Key non esiste sarà restituito NULL.

Es lettura scrittura

private bool LoadAppState()
{
	bool ok = true;
	bool appKeyPresent = false;
	bool statePresent = false;
	try
	{
		RegistryKey key = Registry.LocalMachine.OpenSubKey("Software", true);
		RegistryKey keyAppVersion = null;
 
		string[] allSWAppName = key.GetSubKeyNames();
		foreach (string appName in allSWAppName)
		{
			if (appName == MultiPrepareKTUpdater.Model.Configuration.ApplicationName)
			{
				appKeyPresent = true;
				key = key.OpenSubKey(MultiPrepareKTUpdater.Model.Configuration.ApplicationName, true);
				keyAppVersion = key.OpenSubKey("AppVersion_" + c_AppVersion, true);
				statePresent = keyAppVersion != null;
				break;
			}
		}
 
		// Creazione chiavi di registro
		if (!statePresent)
		{
			if (!appKeyPresent)
			{
				key.CreateSubKey(MultiPrepareKTUpdater.Model.Configuration.ApplicationName);
				key = key.OpenSubKey(MultiPrepareKTUpdater.Model.Configuration.ApplicationName, true);
			}
			keyAppVersion = key.CreateSubKey("AppVersion_" + c_AppVersion);
 
			keyAppVersion = key.OpenSubKey("AppVersion_" + c_AppVersion, true);
			keyAppVersion.SetValue("LastServiceSelected", "nd");
			keyAppVersion.SetValue("LastServiceSelectedVersion", "nd");
			keyAppVersion.SetValue("LastSourcePath", "nd");
		}
		else
		{
			CmbApplicationList.SelectedValue = keyAppVersion.GetValue("LastServiceSelected");
			TxtVersionLabel.Text = keyAppVersion.GetValue("LastServiceSelectedVersion").ToString();
			TxtSourcePath.Text = keyAppVersion.GetValue("LastSourcePath").ToString();
		}
	}
	catch (Exception ex)
	{
		ok = false;
		throw;
	}
	return ok;
}
private bool SaveAppState()
{
	bool ok = true;
	try
	{
		RegistryKey key = Registry.LocalMachine.OpenSubKey("Software", true);
		RegistryKey keyAppVersion = null;
 
		key = key.OpenSubKey(MultiPrepareKTUpdater.Model.Configuration.ApplicationName, true);
		keyAppVersion = key.OpenSubKey("AppVersion_" + c_AppVersion, true);
 
		keyAppVersion.SetValue("LastServiceSelected", CmbApplicationList.SelectedValue.ToString());
		keyAppVersion.SetValue("LastServiceSelectedVersion", TxtVersionLabel.Text.Trim());
		keyAppVersion.SetValue("LastSourcePath", TxtSourcePath.Text.Trim());
	}
	catch (Exception ex)
	{
		ok = false;
		//throw;
	}
	return ok;
}

Array

Concatenare

Concatenare array di stringhe in una nuova somma di tutte, esempio da MSDN Microsoft:

using System;
 
public class JoinTest {
    public static void Main() {
 
        Console.WriteLine(MakeLine(0, 5, ", "));
        Console.WriteLine(MakeLine(1, 6, "  "));
        Console.WriteLine(MakeLine(9, 9, ": "));
        Console.WriteLine(MakeLine(4, 7, "< "));
    }
 
    private static string MakeLine(int initVal, int multVal, string sep) {
 
        string [] sArr = new string [10];
 
        for (int i = initVal; i < initVal + 10; i++)
            sArr[i - initVal] = String.Format("{0,-3}", i * multVal);
 
        return String.Join(sep, sArr);
    }
}
// The example displays the following output:
//       0  , 5  , 10 , 15 , 20 , 25 , 30 , 35 , 40 , 45
//       6    12   18   24   30   36   42   48   54   60
//       81 : 90 : 99 : 108: 117: 126: 135: 144: 153: 162
//       28 < 35 < 42 < 49 < 56 < 63 < 70 < 77 < 84 < 91

Ricerca

Come ricercare in un vettore di stringhe una stringa data. Si usa il metodo dedicato agli Array Array.Find():
string[] arrAttributeToFound = strCSVAttributeList.Split(',');
 
if (!string.IsNullOrEmpty(
	Array.Find(arrAttributeToFound, a => a.EndsWith(substrAttribToFind, StringComparison.OrdinalIgnoreCase))
						))
{
	// ...
}

In questo esempio si ricerca a partire dalla fine perchè si usa: EndsWith. Ed in più è case insensitive!

Sui metodi

Parametri di interfaccia variabili

Per passare ad un metodo un numero variabile di parametri omogenei o non in modo simile a quello usato dall'istruzione string.format(stringFormat, parameters[]);:

 private static void LogSubscriptionMessage(string format, params object[] args)
        {
            //string strInfo4LOG = string.Empty;
 
            if (args != null && args.Length > 0)
            {
                format = String.Format(System.Globalization.CultureInfo.CurrentCulture, format, args);
            }
            logger.Info(format);
        }

Liste

Ricerche

Segue un esempio di ricerca usando LinQ ma che utilizza il metodo Contains() della 'System.Collections.Generic' per verificare che un attributo appartenga ad un insieme rappresentato come lista di numeri:
List<int> aisbasictypes = new List<int>() { 1, 2, 3, };
List<int> aisextendedtypes = new List<int>() { 5 };
 
AisData basicdata = (from AisData a in lstAIVDO
                      where aisbasictypes.Contains(a.type)
                      select a
                     ).FirstOrDefault();
AisData extdata = (from AisData a in lstAIVDO
                     where aisextendedtypes.Contains(a.type)
                     select a
                   ).FirstOrDefault();

La stessa cosa poteva esser risolta inserendo i numeri in una stringa CSV ma l'esempio di sopra può essere usato anche per altri tipi di dati oltre che per interi.

Gestione delle eccezioni

Loggare numero di linea

Di solito il nome del metodo è inserito dal framework di Logging (NLog, log4Net). Il seguente è una estensione dell'oggetto Exception e ricerca il primo elemento dello stack che abbia un numero di riga:

public static int GetFirstLineCodeException(this Exception exc)
{
	int lineaCodice = -1;
	try
	{
		StackTrace st = new StackTrace(exc, true);
		foreach (StackFrame sf in st.GetFrames())
		{
		   lineaCodice = sf.GetFileLineNumber();
		   if (lineaCodice != 0)
		   {
			  break;
		   }
		}
	 }
	 catch (Exception e)
	 {
		lineaCodice = -1;
	 }
	 return lineaCodice;
}

Poi si usa così:

try
{
	//Eccezione
}         
catch (Exception e)
{
	log.ErrorFormat("Errore {0}, {1} Linea {2}.",
				e.HResult, e.Message, e.GetFirstLineCodeException());
	throw;
}

Mappa e Link


C# | Tips programmazione


Visual Studio | Programmazione


ReflectionParole chiave:File, File System, Machine, PC, Join

Author