Zobrazují se příspěvky se štítkemprogramování. Zobrazit všechny příspěvky
Zobrazují se příspěvky se štítkemprogramování. Zobrazit všechny příspěvky

sobota 12. dubna 2008

Programování - ukládání a načítání obrázku z/do databáze (.NET & MSSQL)

  • obrázek je ukládaný v SqlServeru jako typ Image

Načítání obrázku:

   1:  // Načtení prvního obrázku v tabulce do PictureBoxu
   2:  SqlConnection pripojeni = new SqlConnection(pripojovaciRetezec);
   3:  pripojeni.Open();
   4:   
   5:  SqlCommand cmd = new SqlCommand("SELECT * FROM obrazky", pripojeni);
   6:   
   7:  SqlDataReader reader = cmd.ExecuteReader();
   8:  reader.Read();
   9:   
  10:  MemoryStream ms = new MemoryStream( (Byte[])reader["Obrazek"] );
  11:   
  12:  pictureBox1.Image = Image.FromStream(ms);
  13:   
  14:  reader.Close();
  15:  pripojeni.Close();

 

Ukládání obrázku:

 

   1:  // Uložení obrázku do db vybraného pomocí openFileDialogu
   2:  if (openFileDialog1.ShowDialog() == DialogResult.OK)
   3:  {
   4:      string cesta = openFileDialog1.FileName;
   5:   
   6:      SqlConnection pripojeni = new SqlConnection(pripojovaciRetezec);
   7:      pripojeni.Open();
   8:   

9: SqlCommand cmd = new SqlCommand("INSERT INTO obrazky (Obrazek,Nazev)

VALUES (@Obrazek, @Nazev)", pripojeni);

  10:   
  11:      cmd.Parameters.Add(new SqlParameter("Obrazek", SqlDbType.Image));
  12:      cmd.Parameters.Add(new SqlParameter("Nazev", SqlDbType.VarChar));
  13:   
  14:      FileStream fs = new FileStream(cesta, FileMode.Open);
  15:      Byte[] obr = new Byte[fs.Length];
  16:      fs.Read(obr, 0, Convert.ToInt32(fs.Length));
  17:   
  18:      cmd.Parameters["Obrazek"].Value = obr;
  19:      cmd.Parameters["Nazev"].Value = openFileDialog1.SafeFileName;
  20:   
  21:      cmd.ExecuteNonQuery();
  22:   
  23:      pripojeni.Close();
  24:  }



neděle 6. dubna 2008

Programování - Hashové tabulky v C#

  • Hashtable je typ kolekce, nachází se ve jmenném prostoru System.Collections
  • ukládá obecně jakékoliv objekty (typ object) pod určitým klíčem (také object) = jedná se de facto o slovník
  • není možné vložit dvakrát stejný klíč, není možné objekty třídit a nepamatuje si pořadí vkládaných objektů
  • objekt je ukládaný do nějakého vnitřního pole, přičemž index je určený pomocí metody GetHashCode() z našeho klíče (objekt klíče musí tedy tuto metodu implementovat - standardně implementováno u všech typů poděděných od object)
  • poměr zaplněné části tabulky k její kapacitě se nazývá faktor zaplnění,  můžeme ho nastavit a určuje nám kolik položek může být skutečně zaplněno
    • čím menší faktor zaplnění, tím lépe bude hashová tabulka fungovat, ale tím více bude zabírat paměti
  • můžeme v konstruktoru určit základní kapacitu pro jakou si má Hashtable alokovat paměť; výchozí hodnota je 16
    • když se kapacita vyčerpá (v závislosti na faktoru zaplnění), automaticky si Hashtable realokuje paměť; nová kapacita je rovna nejbližšímu prvočíslu, které je větší než dvojnásobek aktuální kapacity
    • slovníky jsou nejefektivnější, když je jejich kapacita definovaná prvočíslem
  • hledání pomocí klíče v Hashtable je velice rychlé
    • implementováno přes indexer
  • přidávání a odebírání objektů je šetrné, není nutné vždycky přesouvat položky v paměti(oproti poli)
  • metoda Add() pro přidávání, Remove() pro odebírání
  • metody ContainsKey() a ContainsValue()
  • pokud jako klíče používáme řetězce, je doporučeno místo Hashtable použít StringDictionary (System.Collections.Specialized)
  • vlastní slovník si můžeme vytvořit poděděním od abstraktní třídy DictionaryBase
   1:  using System;
   2:  using System.Collections.Generic;
   3:  using System.Text;
   4:  using System.Collections;
   5:   
   6:  namespace TeorieHashtable
   7:  {
   8:      class Klic
   9:      {
  10:          string retezec;
  11:   
  12:          public string Retezec 
  13:          { get { return retezec; } set { retezec = value; } }
  14:   
  15:          public Klic(string retezec)
  16:          {
  17:              this.retezec = retezec;
  18:          }
  19:   
  20:          public override string ToString()
  21:          {   
  22:              return retezec;
  23:          }
  24:      }
  25:   
  26:      // vsimnete si volani konstrukturu rodice
  27:      // na procviceni dedicnosti
  28:      class Hodnota : Klic 
  29:      {
  30:          public Hodnota(string retezec) : base(retezec) {}
  31:      }
  32:   
  33:      class Program
  34:      {
  35:          static void Main(string[] args)
  36:          {
  37:              Hashtable kolekce = new Hashtable(51, 0.5f); 
  38:              // nastavili jsme kapacitu na 51 polozek a faktor
  39:              // zaplneni na 0.5, coz znamena ze bude 
  40:              // hashova tabulka zaplnena vzdy jen z jedne poloviny
  41:              
  42:              Klic klic1 = new Klic("abc");
  43:              Klic klic2 = new Klic("xyz");
  44:   
  45:              Hodnota hodnota1 = new Hodnota("hodnota");
  46:   
  47:              // pridani polozek
  48:              kolekce.Add(klic1, hodnota1);
  49:              kolekce.Add(klic2, hodnota1);
  50:   
  51:              Console.WriteLine(kolekce[klic2]); // vypise 'hodnota'
  52:   
  53:              // odebrani polozky
  54:              kolekce.Remove(klic2);
  55:   
  56:              // jak projit vsechny objekty v hashtabulce?
  57:              // pomoci enumeratoru:
  58:              IDictionaryEnumerator enumerator = kolekce.GetEnumerator();
  59:              while (enumerator.MoveNext())
  60:              {
  61:                  Console.WriteLine(enumerator.Key.ToString() + " " +
  62:                                    enumerator.Value.ToString());
  63:              }
  64:   
  65:              // nebo pomoci foreach
  66:              foreach (DictionaryEntry polozka in kolekce)
  67:              {
  68:                  Console.WriteLine(polozka.Key.ToString() + " " + 
  69:                                    polozka.Value.ToString());
  70:              }
  71:   
  72:              // vypise dvakrat 'abc hodnota'
  73:              Console.ReadLine();
  74:   
  75:          }
  76:      }
  77:  }

Programování - Indexery v C#

  • nejedná se o základní vlastnost objektově orientovaného programování
  • jde o syntaktickou vymoženost jazyka pro pohodlnější práci s objektem
  • můžeme k našemu objektu přistupovat jako k poli
    • daný "index" může být i vícerozměrový a není omezen jen na typ int
   1:  using System;
   2:  using System.Collections.Generic;
   3:  using System.Text;
   4:  using System.Text.RegularExpressions;
   5:   
   6:  namespace TeorieIndexery
   7:  {
   8:      class ObjektSIndexerem
   9:      {
  10:          private int[] desetcisel;
  11:          private string testovaciRetezec;
  12:   
  13:          public ObjektSIndexerem()
  14:          {
  15:              desetcisel = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
  16:              testovaciRetezec = "testovaci retezec s cislem 7890";
  17:          }
  18:   
  19:          // indexer vypada podobne jako vlastnost (ma setter a getter)
  20:          // ale misto nazvu pouzivame klicove slovo 'this'
  21:          // kteremu predchazi typ navratove hodnoty
  22:          // a nasleduje typ indexu
  23:          public int this[int index]
  24:          {
  25:              get { return desetcisel[index]; }
  26:              set { desetcisel[index] = value; }
  27:          }
  28:   
  29:          // ukazka jineho indexeru
  30:          // pouze pro cteni, hleda v nasem retezci pomoci 
  31:          // regularniho vyrazu a vrati nalezeny retezec
  32:          // tohle neni typicke pouziti indexeru!!
  33:          // davam to sem pro ukazku ze jde indexer pouzit i jinak
  34:          public string this[Regex regex]
  35:          {
  36:              get { return regex.Match(testovaciRetezec).Value; }
  37:          }
  38:      }
  39:   
  40:      class Program
  41:      {
  42:          static void Main(string[] args)
  43:          {
  44:              ObjektSIndexerem obj = new ObjektSIndexerem();
  45:   
  46:              Console.WriteLine(obj[5]); // vrati 5
  47:   
  48:              obj[5] = 7;
  49:              Console.WriteLine(obj[5]); 
  50:              // vrati 7, protoze jsme dane cislo zmenili
  51:   
  52:              Console.WriteLine(obj[new Regex(@"[0-9]+")]); 
  53:              // vrati '7890'
  54:   
  55:              Console.ReadLine();
  56:          }
  57:      }
  58:  }

sobota 5. dubna 2008

Programování - Polymorfizmus

  • polymorfizmus
    • poly - mnoho
    • morfizmus - tvarost, tvarování
    • = mnohotvarost, různorodost
  • používáme v případě, kdy chceme zajistit různé chování metod potomků některé třídy
  • souvisí s virtuálními a přepsanými metodami (klíčová slova virtual a override)
  • vychází z předpokladu, že můžeme odkazovat na zděděný typ pomocí typu rodiče
    • Rodic b = new Potomek()
    • toto chování je přítomno ve všech moderních OOP jazycích a umožňuje nám například ukládat rodiče a potomky společně do pevně typovaných kolekcí a polí
   1:  using System;
   2:  using System.Collections.Generic;
   3:  using System.Text;
   4:   
   5:  namespace TeoriePolymorfizmus
   6:  {
   7:      class Rodic
   8:      {
   9:          public void nevirtualniMetoda()
  10:          {
  11:              Console.WriteLine("Jsem nevirtualni metoda rodice");
  12:          }
  13:   
  14:          public virtual void virtualniMetoda()
  15:          {
  16:              Console.WriteLine("Jsem virtualni metoda rodice");
  17:          }
  18:      }
  19:   
  20:      class Potomek : Rodic
  21:      {
  22:          public void nevirtualniMetoda()
  23:          {
  24:              Console.WriteLine("Jsem nevirtualni metoda potomka");
  25:          }
  26:   
  27:          public override void virtualniMetoda()
  28:          {
  29:              Console.WriteLine("Jsem prepsana metoda");
  30:          }
  31:   
  32:      }
  33:   
  34:      class Program
  35:      {
  36:          static void Main(string[] args)
  37:          {
  38:   
  39:              Potomek a = new Potomek();
  40:              a.nevirtualniMetoda();
  41:              a.virtualniMetoda();
  42:   
  43:              Rodic b = new Potomek();
  44:              b.nevirtualniMetoda();
  45:              b.virtualniMetoda();
  46:   
  47:              /* Vystup bude: 
  48:               * 
  49:               * Jsem nevirtualni metoda potomka
  50:               * Jsem prepsana metoda
  51:               * Jsem nevirtualni metoda rodice  
  52:               * 
  53:               * // neni totiz jasne zda volame metodu rodice nebo potomka,
  54:               *    zavola se proto metoda rodice i presto ze sme vytvareli objekt
  55:               *    potomka
  56:               * 
  57:               * Jsem prepsana metoda
  58:               * 
  59:               * // tady uz se zavola metoda potomka, protoze jsme ji spravne prepsali 
  60:               */
  61:   
  62:              Console.ReadLine();
  63:   
  64:          }
  65:      }
  66:  }

pátek 4. dubna 2008

Programování: Práce s řetězci v C#/.NET

tato otázka se nezabývá kódováním, můžeme ho proto při výkladu vynechat

  • standardně jsou všechny řetězce v .NET ukládány jako Unicode
  • základní datový typ pro řetězce v C# je System.String, většinou vytvářený pomocí klíčového slova string (s malým "s")
    • je vždy uložen na heapu (haldě; podobně jako jiné základní typy, např. int)
    • při manipulaci s řetězcem (např. při přidání jednoho znaku) je vždy nutné vytvořit nový řetězec a starý smazat => není proto vhodný pro časté změny
    • s řetězcem můžeme pracovat s přetíženými operátory (=,+=,+)
    • String má zabudovaný indexer, který vrací daný znak na pozici i (jako char): mujretezec[i]
    • důležité metody:
      • Compare() a CompareOriginal() porovnávají řetězce (první zmíněná podle místního a jazykového nastavení), použití přes statickou třídu String nebo přes přetížený operátor (==,!=)
      • IndexOf() pro hledání podřetězce, vrací pozici prvního znaku z prvního nelezeného podřetězce
      • Replace() sloužící pro nahrazování znaků a podřetězců
      • Remove() pro odstranění zadaného počtu znaků od zadané pozice
      • Split() sloužící k rozdělení řetězců podle zvoleného oddělovače (např. ";")
      • Substring() extrahující podřetězec od zadané pozice
      • ToCharArray() která vrátí pole charů
    • vlastnost Length (readonly), která vrací počet znaků v řetězci
  • pro rychlejší manipulaci s řetězcem se požívá třída StringBuilder
    • při vytváření instance objektu můžeme specifikovat, kolik znaků v paměti chceme pro řetězec rezervovat, můžeme tím předejít zbytečnému kopírování, pokud by se změněný řetězec nevešel do rezervovaného bloku paměti
    • třída má podobné metody jako String, pro skládání řetězců se však používá metoda Append()
    • další důležitou metodou je ToString(), který vrátí daný řetězec přetypovaný na System.String
  • jednou z možností reprezentace řetězce je použití charového pole
  • pro pokročilou práci s řetězci, zejména pro hledání, se používají regulární výrazy
    • potřebné třídy najdeme ve jmenném prostoru System.Text.RegularExpressions
    • základní třídy: Regex, Match

Kreslení řetezců v GDI+

  • základní metoda pro kreslení řetězců třídy Graphics je DrawString()
    • spousta přetížení
    • základní DrawString("řetězec", Font, Brushes.Black, x, y)
    • Font je vlastnost formuláře, můžeme si však naistancovat vlastní písmo:
      • new Font(FontFamily.GenericSansSerif, Font.Size)
    • Brush je abstraktní typ, pokud si chci naistancovat vlastní štětec, musím použít nějaký zdědený typ, např. SolidBrush
    • volitelně lze přidat ještě parametr StringFormat, kterým můžeme dále specifikovat formátování řetězce
      • např. chceme zobrazit text vertikálně:
      • new StringFormat(StringFormatFlags.DirectionVertical | tady lze přidat další flagy)
    • standardní systémový font má velikost 13!
  • řádkování se dá řešit několika způsoby
    • pomocí změření velikosti jednoho řádku metodou Graphics.MeasureString()
    • lepší varianta je však použití Font.GetHeight(Graphics)
      • výhodou je, že nám bude řádkování fungovat i při používání různých transformací