En iyi yanıtlayıcılar
SQL Server Çok kriterli sorgulama hakkında

Soru
-
Merhaba Arkadaşlar,
Öncelikle geçmiş kurban bayramınız mübarek olsun.
Çoklu sorgulama konusunda yardımınıza ihtiyacım var. Yani raporlar form’umdaki kriterlere göre verileri datagridview de listelemek istiyorum.
Örneğin. 5-6 Adet tablom var. Şu şekilde yapmak istiyorum. Aşağıdaki yarım sorgularda tablolarımı belirttim.Gerisini tam olarak nasıl yapacağımı bilmediğim için ….. şekilye yaptım. Oradan başlayabilirizJ
Ben checkbox1’ seçeceğim sipariştarih1’e başlanğıç tarihimi ve sipariştarih2’ye bitiş tarihimi yazıp iki tarih arasında verilen siparişleri listeyebileceğim.
Ben hem chekcbox1’i ve hem checkbox4’ ü seçeceğim kriterleri belirtip btnraporal’a tıkladığımda bana o iki tarih arası x ürünleri listemesini istiyorum. Ancak o tarihler arası x ürün yok ise boş gelecek. Yani yapmak istediğim ben kriterleri seçeceğim hangisi veritabanımda mevcut ise datagridview de listeleyeceğim. VB.NET 2010 SQLSERVER 2008.
Private Sub btnraporal_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnraporal.Click
If CheckBox1.Checked = True Then
cmd = New SqlCommand
cmd.Connection = cn
cmd.CommandText = "Select * FROM SIPARISLER .............siparistarih1.text and siparistarih2 "
adap=New SqlDataAdapter=cmd)
dt = New DataSet
adap.Fill(dt, "SIPARISLER")
DataGridView1.DataSource = BindingSource1
Else
If CheckBox2.Checked = True Then
cmd = New SqlCommand
cmd.Connection = cn
cmd.CommandText = "Select * FROM TESLIMATLAR .............teslimtarih1.text and teslimtarih2 "
adap=New SqlDataAdapter=cmd)
dt = New DataSet
adap.Fill(dt, "TESLIMATLAR")
DataGridView1.DataSource = BindingSource1
Else
If CheckBox3.Checked = True Then
cmd = New SqlCommand
cmd.Connection = cn
cmd.CommandText = "Select * FROM FIRMALAR .............txtfirma.text"
adap=New SqlDataAdapter=cmd)
dt = New DataSet
adap.Fill(dt, "FIRMALAR")
DataGridView1.DataSource = BindingSource1
Else
If CheckBox4.Checked = True Then
cmd = New SqlCommand
cmd.Connection = cn
cmd.CommandText = "Select * FROM SIPARISLER .............txtsiparisürün.text"
adap=New SqlDataAdapter=cmd)
dt = New DataSet
adap.Fill(dt, "SIPARISLER")
DataGridView1.DataSource = BindingSource1
Else
If CheckBox5.Checked = True Then
cmd = New SqlCommand
cmd.Connection = cn
cmd.CommandText = "Select * FROM TESLIMATLAR .............txtgelenürün.text "
adap=New SqlDataAdapter=cmd)
dt = New DataSet
adap.Fill(dt, "TESLIMATLAR")
DataGridView1.DataSource = BindingSource1
Else
If CheckBox6.Checked = True Then
cmd = New SqlCommand
cmd.Connection = cn
cmd.CommandText = "Select * FROM FIRMALAR .............txtşehir.text "
adap=New SqlDataAdapter=cmd)
dt = New DataSet
adap.Fill(dt, "FIRMALAR")
DataGridView1.DataSource = BindingSource1
End If
End If
End If
End If
End If
End If
End Sub
- Düzenleyen Emre GunerturkModerator 22 Kasım 2010 Pazartesi 13:41 tekrar
- Taşıyan Emre GunerturkModerator 7 Şubat 2011 Pazartesi 10:16 (Gönderen:Visual Studio Forumu)
Yanıtlar
-
Bu seninkinin parametreli hali:
If TxtFirmaAdı.Checked = True And TxtŞehirAdı.Checked = True Then cmd.CommandText = "Select * From Firmalar Where Unvan = @unvan And Sehir = @sehir" ElseIf TxtFirmaAdı.Checked = True Then cmd.CommandText = "Select * From Firmalar Where Unvan = @unvan" ElseIf TxtŞehirAdı.Checked = True Then cmd.CommandText = "Select * From Firmalar Where Sehir = @sehir" Else cmd.CommandText = "Select * From Firmalar" End If cmd.Parameters.AddWithValue("@unvan", txtfirmaara.Text) cmd.Parameters.AddWithValue("@sehir", txtşehir.Text) adap = New OleDbDataAdapter(cmd) dt = New DataSet adap.Fill(dt, "Firmalar") BindingSource1.DataSource = dt BindingSource1.DataMember = dt.Tables(0).TableName DataGridView1.DataSource = BindingSource1
Bu da onun yerine Linq kullanan sekli (tam aynisi degil - ornegin K yazarak K ile baslayanlar. Digerinde bilemedim Access oldugu icin - Accessin dilini anlamak muamma)
Dim sorgu As DataView Dim unvan As String = txtfirmaara.Text.ToUpper(New CultureInfo("tr-TR")) Dim sehir As String = txtşehirara.Text.ToUpper(New CultureInfo("tr-TR")) If (TxtFirmaAdı.Checked And TxtŞehirAdı.Checked) Then sorgu = (From kayit In dt.Tables("Firmalar") Where kayit.Field(Of String)("Unvan").ToUpper(New CultureInfo("tr-TR")).StartsWith(unvan) AndAlso kayit.Field(Of String)("Sehir").ToUpper(New CultureInfo("tr-TR")).StartsWith(sehir) Select kayit).AsDataView() ElseIf TxtFirmaAdı.Checked Then sorgu = (From kayit In dt.Tables("Firmalar") Where kayit.Field(Of String)("Unvan").ToUpper(New CultureInfo("tr-TR")).StartsWith(unvan) Select kayit).AsDataView() ElseIf TxtŞehirAdı.Checked Then sorgu = (From kayit In dt.Tables("Firmalar") Where kayit.Field(Of String)("Sehir").ToUpper(New CultureInfo("tr-TR")).StartsWith(sehir) Select kayit).AsDataView() Else sorgu = (From kayit In dt.Tables("Firmalar") Select kayit).AsDataView() End If BindingSource1.DataSource = sorgu
Tabii Linq ve DataSet tirmalamak demek. Dataset olmasa daha iyi. Ancak kafan karismasin, kodun zaten gidecek cok yolu var (mesela public kullanma, tekrarlari onle vs), hepsini hemen ogrenmeye calisma:)
Not: VB gercekten cok zormus. Bundan sonra grekirse C# ile cevap vermeyi tercih ediyorum.
- Yanıt Olarak İşaretleyen Emre GunerturkModerator 28 Kasım 2010 Pazar 19:56
Tüm Yanıtlar
-
Merhabalar öncelikle sizinde Bayramınız Mubarek olsun.
iç içe if kullanmak şu an için sizi daha da karıştırmanıza ve kod yığının fazlalaşmasına yol açacağı için tavsiye olarak
if ve elseif blocklarını kullanmanızı tavsiye edebilirim.
örnek :
If CheckBox1.Checked = True Then
Elseif CheckBox2.Checked = True Then
Elseif CheckBox3.Checked = True Then
Elseif CheckBox4.Checked = True Then
Elseif CheckBox5.Checked = True Then
Elseif CheckBox6.Checked = True Then
else
şeklinde hangi checkbox seçili ise onu yapacaktır.
eğer birinci seçili diğerleride seçili ise sadece birini yapar
-
Merhaba Emre Bey,
Öncelikle tşk.ederim tavsiyeniz için.
Ancak birinci checkbox seçili diğerleri de seçili ise seçili olanları dikkate almasını istiyorum. Yani checkbox ların kaçtanesi seçili ise bu seçimleri dikkate almasını istiyorum.Seçili olmayanları boş geçecek dikkate almayacak.
Yani örnek olarak şöyle söyleyeyim. X1tarih ile X2 tarih arasında şu isimdeki ürünleri listele veya X1tarih ile X2 tarih arasında şu isimdeki ürünlerden teslim alınanları belirtmiş olduğum teslim tarihleri arasındakileri listele diyebilmem gerekiyor.
Dediğiniz şekilde aklıma geldi ben bütün kriterleri seçsem de sadece 1.yi dikkate alacak ama benim işime yaramıyor.
Benim yapmak istediğim çok kriterli sorgu. Sebebi ise kriterlere uygun rapor alabilmek.
-
Demek istediğinizi anladım sanırım birde emin olalım Şimdi tarihlerin seçili olup olmadığını kontrol etmek istiyorsunuz ?
onun ardından db üzerinde o tarihler arasındaki verileri firmalar siparişler vb verileri ayrı ayrı göstermek istiyorsunuz eğer seçilmiş ise ?
hepsi seçili ise hepsi listelenecek yok bazıları seçili ise seçilenler listelenecek ?
-
Evet dediğiniz gibi hem tarihlerin seçili olup olmadığını kontrol ettirmek istiyorum tabi aynı zamanda diğer chekcbox lar da seçilimi değil mi onları da kontrol edecek.
Seçili olanları dikkate alarak verileri listeyecek.
Örneğin checkbox1 seçili dikkate alacak. checkbox2 seçili değil dikkate almayacak. checkbox3 seçili dikkate alacak. checkbox4 seçili dikkate alacak. Örnek olarak yazdım.
dikkate aldıklarını sorgulayıp kriterlere uyanları dgrid'de listeleyecek.
Syg.
-
Ne anlatilandan ne de koddan ne yapmak istedigini tam olarak anlayamadim:( Checkbox'larda ne oldugunu filan kabaca gorebilseydik iyi olurdu. Dinamik SQL yazmayi bu sekilde if ... end if bloklariyla yapabilirsin ama belki de ihtiyacin CommandText'in ve parametrelerin dinamik olarak eklenmesidir. Ornegin:
StringBuilder sb = new StringBuilder();
sb.Append("Select * from");if (...)
sb.AppendFormat(" {0} where ", tabloAdi);Senin koda bakinca bu olmaz diye dusunuyorum aslinda. Bir taraftan da o "ELSE" ler kafa karistiyor. Formunun bir goruntusunu gorebilseydik iyi olurdu. Bu arada SQL cumlesi asla degeri ...text diye icermemeli, mutlaka parametre kullan.
Select
* FROM TESLIMATLAR where tarih = teslimtarih1.text
YAZMA.
Select * FROM TESLIMATLAR where tarih = @teslimTarihi
yaz ve parametre ekle. cm.Parameters.AddWithValue("@teslimTarihi",DateTime.Parse(teslimtarih1.text)) gibi.
Bir de nacizane tavsiyem, boyle SQL ile ugrasmak yerine (ozellikle T-SQL'e hakim degilsen) Linq kullanman. Linq kullanirsan hem sorgunu dinamik olarak olusturabilirsin hem de Linq senin icin SQL'i yazar. T-SQL yerine "Object Query" yani nesne sorgusu kullandigindan sana da daha dogal gelebilir ve intellisense destegi var.
-
Mrb.CetinBasoz,
Anlaşılmamasının sebebi benim anlatım eksikliğim olduğu kesin:)
Ben daha anlaşılır şekilde hazırlayıp bu konu altında tekrar soracağım gerekirse projemi paylaşacağım.
Link kullanmayı bilmiyorum. Tavsiyeniz için çok tşk.ederim. Dediğiniz gibi T-SQL 'e hakim değilim bilgim az ama öğrenmek istiyorum,İnşallah kısa zamanda öğrenirim:)
-
Mrblar ,
Ben tekrar düzenledim ve formun resmini de ekledim. http://cid-a3ca9c7a87cd619b.office.live.com/browse.aspx/.Documents?uc=2 bu linkten erişilebilir.
Aşağıda yazmış olduklarım yapmak istediklerimin benzer örneğidir.
CheckBox lar karışıklık yaratıyor sanırım. CheckBox kullanmayalım
Öncelikle veritabanımdan başlayayım.
Veritabanı Adı: Stokdb
Tablolarım ( FIRMALAR , SIPARISLER , GELEN_URUN , CIKAN_URUN )
FIRMALAR tablosu: ( FIRMAID , FIRMA_ADI , YETKILI , ADRES , SEHIR , ILCE , TEL1 , TEL2 , FAKS , MAIL , VD , VNO )
SIPARISLER tablosu: ( SIPARISID , FIRMAID , SIPARIS_TARIH , SIPARIS_URUN_ADI , SIPARIS_ADET , BIRIM_FIYAT , KDV_HARIC_FIYAT , KDV_DAHIL_FIYAT )
GELEN_URUN tablosu : ( GELENID , FIRMAID , GELEN_URUN_ADI , GELEN_URUN_ADET , GELEN_TARIH , TESLIM_ALAN )
CIKAN_URUN tablosu: ( CIKANID , FIRMAID , CIKAN_URUN_ADI , CIKAN_ADET , KALAN_ADET )
Raporlar Formu üzerinde 4 Adet DateTimePicker , 7 adet Textbox , 1 adet buton var.
İsimleri Aşağıdaki şekilde.
( textSipariş_Tarih1 ) , ( textSipariş_Tarih2 ) , ( textSipariş_Ürün ) , ( textGelen_Tarih1 ) , ( textGelen_Tarih2 ) , ( textGelen_Ürün_adı ) ,
( textfirma_adı ) , ( textşehir ) , ( textürün_Adı ) , ( textbaslangıc_fiyat ) , ( textbitiş_fiyat )
Ben Raporlar Formu mu açıp rapor almak istediğimde Sipariş Tarih1’den Başlanğıç Tarihimi Seçeceğim , SiparişTarih2’den Bitiş Tarihimi seçeceğim.
Sonra devam edip textfirma_adı’na firma adını yazacağım ve yine devam edip textsipariş_Ürün’e ürün ismini yazacağım ve buton1’ bastığımda o tarihler arası belirtmiş olduğum firma ismi ve belirtmiş olduğum ürün’ü datagridview de listeleyeceğim.
Burada ekleyerek devam edebilirim yani fiyatları veya adetleri de dahil edip buton1 bastığımda Tarihleri ve Textbox ları kontrol edip belirtmiş olduğum kriterlere uyan verileri datagridview de listeleyeceğim.
Umarım anlatabilmişimdir.
Anlaşılır değil ise eğer yarın projemi rarlayıp getireceğim gerekirse paylaşacağım.
Yardımcı olmaya çalıştığınız için tşk.
-
Merhaba Levent,
bunun için en mantıklısı şudur;
öncelikle sorguda kullanma ihtimalin olan tüm tabloları birbiriyle JOIN edip bir View içerisine eklersin. Bu view'in adının V_GetSiparis olduğunu düşünelim. Ardından program tarafına geçip bir SQL cümlesi oluşturursun.
string SqlQueryStr ="SELECT * FROM V_GetSiparis WHERE 1=1";
Ardından aşağıdaki gibi IF deyimleriyle SQL cümlesini oluşturursun. Örneğin sipariş tarihleri için aşağıdaki if'i yazarsın
if (textSipariş_Tarih1.Text != "" && textSipariş_Tarih2.Text != "") SqlQueryStr += " AND SIPARIS_TARIH between '" + textSipariş_Tarih1.Text + "' AND '" + textSipariş_Tarih2.Text + "'";
Firma adı için doğrudan şöyle yazabilirsin.
SqlQueryStr += " AND FIRMA_ADI LIKE '"+ textfirma_adı.Text +"'";
Veya şöyle yazabilirsin hiç farketmez
if(textfirma_adı.Text !="") SqlQueryStr += " AND FIRMA_ADI LIKE '"+ textfirma_adı.Text +"'";
bu şekilde tüm alanları IF içerisine ekleyip View üzerinden sorgulama yapabilirsin.
Umarım doğru anlamış ve yardımcı olabilmişimdir.
Ahmet Kaymaz
http://www.ahmetkaymaz.com
SQL Server & C# bloglama -
Bende bir öneri eklemek isterim. İlk okulda öğrendiğimiz bileşim ve kesişim kümelerini hatırlayınız, her filitre sorgusunun bir sonuç kümesi ve bunun bileşim kümesininde sizin istediğiniz sonuç olduğunu düşünürsek;
select * from Siparişler where sipariş_tarihi between @starih1 and @starih2
UNION
select * from Teslimatlar where teslimat_tarihi between @ttarih1 and @ttarih2
UNION
select * from Firmalar where firma_adı LIKE '%' + @firmaadı + '%'
UNION
bıdı
UNION
bıdı
.şeklinde ki sorguyu çheckbox larınızın state lerine göre oluşturur ve parametrelerini eklerseniz nokta atışı yapmış olursunuz. Burada dikkat edilecek şey aynı tablodan birden fazla sorgu olur ve şartları uyarsa aynı kayıttan birden fazla olur bunun için INTERSECT(Kesişim) kullanılması gerekebilir
The God / www.club-bravo.com -
Mrb. Ahmet Bey,
Öncelikle tşk.ederim yardımcı olmaya çalıştığınız için. cvp larım biraz gecikebilir yoğumluğumdan dolayı bilmenizi isterim.
Formun resmini ekledim baktınızmı bilmiyorum:)
Ben beirttiğiniz gibi deneyeceğim olurda yapamazsam tekrar burada sorarım.Ancak yazdığınız kodlarda anlayamadığım bir kaç nokta var.
örneğin: bu sorguda (
if (textSipariş_Tarih1.Text != "" && textSipariş_Tarih2.Text != "") SqlQueryStr += " AND SIPARIS_TARIH between '" + textSipariş_Tarih1.Text + "' AND '" + textSipariş_Tarih2.Text + "'"; )
" ! " bu neyi ifade ediyor?
bu kodları ancak akşam evde deneyebilirim. projem evde çünkü.yarın sonuca burada paylaşırım.
Tekrar tşk.
-
-
Merhaba Levent,
Gonderdigin goruntu ve word dosyasi cok faydali oldu. Sanirim daha onceki o Checkbox'lar aslinda datetimepicker'larin checkboxlari idi (Null destegi icin). Sana hem kod ornegim var anladigim kadariyla hem de birkac fikir. Lutfen bunu elestiri gibi algilama, uzun yillar ugrasinin sonu gordugum zorluk kolaylik onerileri:
-Kontrollerinin adlarinin tipleri ile uyumlu olmasinda fayda var ve genelde onerilen kontrolun adinin ilk iki ila dort harfinin tipini belirtmesi: textSiparis_Tarih1 yerine dtSiparis_Tarih1, textFirma_Adi yerine txtFirma_Adi gibi. dt on eki onun bir datetimepicker oldugunu dolayisiyla .Value propertysinin DateTime oldugunu hatirlatiyor.
-Kontrollere verdigin isimlerde bence Turkce harf kullanma. .Net gayet guzel kullaniyor ve problem cikmiyor gibi gorunuyor ama bazi durumlarda cikiyor (mesela "ı" harfi ozellikle konfigurasyon/kalip vb dosyalarin derleme sirasinda sacmalamasina yol acabiliyor - en azindan eski versiyonlar ve 3.parti kod jeneratorleriyle basima geldi, bulana kadar gobegim catladi).
-Isimlerde alttan cizgi uzun vadede bunaltiyor:) Onun yerine "Pascal/Camel casing" kullan bence. txtFirma_Adi yerine txtFirmaAdi gibi.
Bunlar kisisel tercihler olarak da yorumlanabilir (bazilari dogrudan onerilen isimlendirmelerden), ben bunlarla rahat ediyorum:)
-Bir de tablolar ve sonucta yapmak istedigin (anladigim kadariyla) SQL ile ilgili. Firmalar ile Siparisler ve Gelen_Urun arasinda FirmaID uzerinden bir iliski goruluyor ama Siparisler ile Gelen_Urun arasindaki iliski supheli geldi. Muhtemelen urun_adi uzerinden ama oyleyse benim kanaatimce tehlikeli bir baglanti. Urunler diye bir tablon olsa da oradan gelen UrunID anahtar degeri kullanilsa iyi olur diye dusunuyorum.
Anladigim cercevede kod (Uyari, C#'la calisiyorum ve VB bana yabanci, garip gorunebilir:)
Dim whereClause As String = "" Dim siparisTarih As String = "" Dim gelisTarih As String = "" Dim fiyat As String = "" Dim isNumberFiyat1 As Boolean Dim isNumberFiyat2 As Boolean Dim fiyat1 As Decimal = 0 Dim fiyat2 As Decimal = 0 If (textSipariş_Tarih1.Checked And textSipariş_Tarih2.Checked) Then siparisTarih = "sip.SIPARIS_TARIH between @sipTarih1 and @sipTarih2" ElseIf (textSipariş_Tarih1.Checked) Then siparisTarih = "sip.SIPARIS_TARIH >= @sipTarih1" ElseIf (textSipariş_Tarih2.Checked) Then siparisTarih = "sip.SIPARIS_TARIH <= @sipTarih2" End If If (siparisTarih <> "") Then whereClause = whereClause + If(whereClause = "", " where ", Environment.NewLine + " and ") + siparisTarih End If If (textGelen_Tarih1.Checked And textGelen_Tarih2.Checked) Then gelisTarih = "gel.GELEN_TARIH between @gelTarih1 and @gelTarih2" ElseIf (textGelen_Tarih1.Checked) Then gelisTarih = "gel.GELEN_TARIH >= @gelTarih1" ElseIf (textGelen_Tarih2.Checked) Then gelisTarih = "gel.GELEN_TARIH <= @gelTarih1" End If If (gelisTarih <> "") Then whereClause = whereClause + If(whereClause = "", " where ", Environment.NewLine + " and ") + gelisTarih End If If (textSipariş_Ürün.Text <> "") Then whereClause = whereClause + If(whereClause = "", " where ", Environment.NewLine + " and ") + _ "sip.SIPARIS_URUN_ADI = @sipUrunAdi" End If If (textGelen_Ürün_adı.Text <> "") Then whereClause = whereClause + If(whereClause = "", " where ", Environment.NewLine + " and ") + _ "gel.GELEN_URUN_ADI = @gelUrunAdi" End If If (textfirma_adı.Text <> "") Then whereClause = whereClause + If(whereClause = "", " where ", Environment.NewLine + " and ") + _ "fir.FIRMA_ADI = @firmaAdi" End If If (textşehir.Text <> "") Then whereClause = whereClause + If(whereClause = "", " where ", Environment.NewLine + " and ") + _ "fir.SEHIR = @sehir" End If isNumberFiyat1 = [Decimal].TryParse(textbaslangıc_fiyat.Text, NumberStyles.Number, Nothing, fiyat1) isNumberFiyat2 = [Decimal].TryParse(textbitiş_fiyat.Text, NumberStyles.Number, Nothing, fiyat2) If (isNumberFiyat1 And isNumberFiyat2) Then fiyat = "sip.BIRIM_FIYAT between @fiyat1 and @fiyat2" ElseIf (isNumberFiyat1) Then fiyat = "sip.BIRIM_FIYAT >= @fiyat1" ElseIf (isNumberFiyat2) Then fiyat = "sip.BIRIM_FIYAT <= @fiyat2" End If If (fiyat <> "") Then whereClause = whereClause + If(whereClause = "", " where ", Environment.NewLine + " and ") + fiyat End If Dim con As New SqlClient.SqlConnection("server=.\SqlExpress;Trusted_Connection=yes;Database=myDatabase") Dim cmd As New SqlClient.SqlCommand() cmd.Connection = con cmd.Parameters.AddWithValue("@sipTarih1", textSipariş_Tarih1.Value) cmd.Parameters.AddWithValue("@sipTarih2", textSipariş_Tarih2.Value) cmd.Parameters.AddWithValue("@gelTarih1", textGelen_Tarih1.Value) cmd.Parameters.AddWithValue("@gelTarih2", textGelen_Tarih2.Value) cmd.Parameters.AddWithValue("@sipUrunAdi", textSipariş_Ürün.Text) cmd.Parameters.AddWithValue("@gelUrunAdi", textGelen_Ürün_adı.Text) cmd.Parameters.AddWithValue("@firmaAdi", textfirma_adı.Text) cmd.Parameters.AddWithValue("@sehir", textşehir.Text) cmd.Parameters.AddWithValue("@fiyat1", fiyat1) cmd.Parameters.AddWithValue("@fiyat2", fiyat2) cmd.CommandText = "SELECT *" + _ " FROM firmalar fir" + _ " left join siparisler sip on sip.firmaID = fir.FirmaID" + _ " left join gelen_urun gel on gel.FirmaID = fir.FirmaID" + _ whereClause
Not: Nasil yaparsan yap ama daha once soyledigim gibi asla:
"select ... where firmaAdi = '" + textFirmaAdi.Text + ..
gibi SQL cumlesi olusturma, daima parametre kullan.- Düzenleyen CetinBasozEditor 23 Kasım 2010 Salı 14:50 duzeltme
- Yanıt Olarak Öneren Emre Aras 23 Kasım 2010 Salı 15:47
-
Merhaba CetinBasoz ,
Baştan eksik anlattım görsel olarak destekli ve detaylı bir şekilde yazıp sormam gerekirdi. Önerilerinizi eleştiri gibi algılamıyorum önerileriniz benim için altın değerindedir. Çünkü ben yeni yeni öğreniyorum sizin Sql bilginizin yanında ben cahil sayılırım:)
Sizlerden öğrendiklerimle inşallah adım adım ilerleyeceğim. Kontrol isimlerinde dediklerinizi uygulayacağım.
Tablolar arası ilişkide ben hepsini FirmaID üzerinden ilişkilendirmeyi düşünmüştüm ama sanırım yanlış yapmışım.
Bu ilk yapmaya çalıştığım stok proğramım. Bilmiyorum mümkün mü ama sizden örnek bir stok veritabanı rica etsem türkçe olursa çok sevinirim.
Veya buraya örnek stokdb nin Tabloları ve içeriklerini yazabilirsiniz. Yada benim stokdb 'de düzeltme yapıp burada paylaşırsanız çok sevinirim. Bende sizin örneğiniz üzerinden devam ederim. Tabi mümkün ise size zahmet vermek istemem.
Bu arada yoğun olduğumdan dolayı cvp lar biraz gecikiyor kusura bakmayın.
Yazmış olduğunuz kodları deneyip sonucu sizinle paylaşacağım.
Yardımlarınız ve önerileriniz için çok tşk.ederim hayırlı akşamlar.
-
Benim calistigim veritabnlarinin sadece birisi stokla ilgili ama ne yazik ki onu veremem (musteriyle yaptigim anlasma o sekilde idi) - gerci o oldukca karmasik sana fayda yerine zarar verir.
SQL server ya da Access ile gelen meshur Northwind database var. O bir cesit stok veritabani. SQL Express starter kitlerinde de bir tane var:
http://www.microsoft.com/sqlserver/2005/en/us/express-starter-schemas.aspx#8
AdventureWorks bir digeri ama baslangic icin karmasik. Bence Northwind ile basla.
-
Mrb.CetinBasoz ,
Veritabanı önerin için tşk inceliyorum şu an. yalnız sizin yazmış olduğunuz kod bana çok karışık geldi akşam uğraştım ama bir türlü yapamadım. Sanırım checkbox lar benim kafamı karıştırıyor.Yanlış anlamayın siz gayet güzel yazmışsınız fakat ben anlayamadım yani sorun bende. Sizden ricam checkbox kullanmadan bir kritere göre örnek yazarmısınız mesela sipariş tarihi örnek olarak yazıyorum sorguda yazım hatası olabilir.
(''select * FROM SIPARISLER WHERE SIPARIS_TARIH BETWEEN @STARIH1 AND @STARIH2'')
cmd.Parameters.AddWithValue("@sipTarih1", textSipariş_Tarih1.Value)
cmd.Parameters.AddWithValue("@sipTarih2", textSipariş_Tarih2.Value)Biraz daha sade bir anlatım rica ediyorum . Benim anlayabileceğim şekilde:)
Dediğim gibi ben anlayamadım kafam karıştı. Bilmediğim kodlar olunca çıkamadım işin içinden ( Environment.NewLine )
Kusura bakmayın uğraştırdım sizi.
Syg.
-
Sanırım iş gittikçe zorlaşacak sizin için; umarım C# la yazılmış olması zorluk çıkarmaz sizin için
http://img695.imageshack.us/img695/4820/filtersample.jpgProjeyide buradan download edebilirsiniz;
http://cid-1ee4adebc4f2eb78.office.live.com/self.aspx/.Public/DataFilterSample.rar
The God / www.club-bravo.com
-
DateTimePicker kontrolunun ShowCheckBox propertysi var. Bunu true yaparsan yaninda bir check box cikiyor (senin goruntude yoktu). Normalde kullanici bir tarih girmek zorunda, bu checkbox var ise onun isaretini kaldirarak deger NULL (VB'de nothing) olabiliyor. Yani kullaniciyi tarihlweri girmek zorunda birakmiyorsun. Oyle olunca olasilik:
if ( tarih1 ve tarih2 girildiyse )
Tablodan ( tarih1 - tarih2 ) araligini sec
"select * from tabloAdi where siparisTarihi between @tarih1 and @tarih2"
elseif (sadece tarih1 girildiyse)
Tablodan ( tarih1 ) ve sonrasini sec
"select * from tabloAdi where siparisTarihi >= @tarih1"
elseif (sadece tarih2 girildiyse)
Tablodan ( tarih2 )'ye kadar olanlari sec
"select * from tabloAdi where siparisTarihi <= @tarih2"
else ( bu kismi yazmaya gerek yoktu )
Tum kayitlari sec
"select * from tabloAdi"
endifOrada yapilan selectin kendisi yerine doldurulan alanlara gore "where" kismini insa ediyoruz. En sonda select'in ana govdesine "where ..." ekliyoruz. O nasil olsa bir string. Kriterlere gore insa etmek mumkun. Her seferinde tum parametreleri SqlCommand cmd'nin Parameters koleksiyonuna ekliyoruz. Kullanilmayan parametrelerin eklenmis olmasi sorun olmuyor cunku o parametreler kullanilmiyor (olusan SQL cumlesinde yoksa). Parametre saysisi az oldugundan bu sekilde gereksiz olanlari dahi eklemenin bir sakincasi yok.
Formuna gecici olarak bir "multiline" true olan textbox koy (textSQL adi olsun). Click kodunda SQL'i calistirmak yerine (cmd.ExecuteQuery vs):
textSQL.Text = cmd.CommandText
koy ve degisik degerlerle nasil bir SQL yazildigini izle. Environment.Newline orada gereksiz. Sadece boyle bir textbox'ta yazilani izlemek istersen ya da debugging sirasinda SQL server Management Studio "new query" alanina filan kopyelersen cok uzun tek satir gormek yerine "where" parcalarini satir satir gor diye.
Not: Environment.Newline kod yazarken [enter]'a basip alt satira gecmek gibi. CR ve LF karakterlerini ekliyor (ASCII 13 ve 10). Windows formsda ise CRLF ile alt satira gecilirken, HTMLde < br > gibi bir tag gerekiyor. CRLF olarak belirtmek yerine Environment.Newline kullaninca .Net ortama gore hangisi kullanilacak iuse onu kullaniyor.
Madem baslardasin ve ogreniyorsun, o zaman Linq'ya bakmayi ihmal etme derim. Ingilizcen iyi ise benim blogda da anlatmaya calistim:
-
Mrb, Önay 'AmonRa' YALÇINER
,
Tşk.Ederim projeyi indirip inceleyeceğim.
İşyeri internetim kısıtlı olduğu için cvp ları başka pc lerden yazmak zorunda kalıyorum.
İşyeri bilgisayarımda sql yüklü değil. Ancak evdeki bilgisayarımda yüklü.İşyerimde fırsat buldukça acces db de deniyorum:)
Yardımcı olmaya çalışan bütün arkadaşlara tşk.ederim. Ben bu konu üzerinde biraz çalışayım. daha da olmaz ise db yi acces yapıp projeyi acces db ile birlikte paylaşacağım.
Çetin bey'in yazmış olduğu örnekler ile çalıyorum şu an birde sizin örneklere bakayım en kısa zamanda olumlu yada olumsuz ( projeyi acces db ile paylaşarak ) dönüş yapacağım:)
İyi günler.
Syg.
-
-
Mrb, CetinBasoz,
Dediğiniz gibi Sql kullanıyorum.Fakat işyerimdeki bilgisayarıma sql kuramadım bir türlü. ( Domain'e dahil edildim o yüzden hata veriyor sanırım.) Oyüzden acces ile öğreniyorum sql de uyguluyorum.:)
http://cid-a3ca9c7a87cd619b.office.live.com/browse.aspx/.Documents?uc=2
Sizden bir konu hakkında ricam olacak ben tablolar arası ilişkiyi bir türlü kuramadım.Ekteki linkte Acces db var tablo larımı ve alanlarımı oluşturdum fakat ilişkiyi yapamadım.Acaba tabloları ilişkilendirmede bana yardımcı olabilirmisiniz rica etsem.Gerekirse değişik te yapabilirsiniz önemli değil.
-
Tablolar arasindaki iliskiyi ben de kuramadim. Gereksiz tekrarlar var gibi. Bence once "data normalization" konularina bak. Ornegin, urunler tablosunda firmaID olmamasi gerekiyor (ama ben senin veri tabanini anlamaya calisiyorum, yanilmis olabilirim). Orada sadece urunun kendisine ait "kimlik" bilgileri olmali. Bir urun degisik firmalardan temin edilebilir (firmalar urunleri saglayan distributorler anladigim). Firma bilgileri bir tabloda, urun bilgileri bir tabloda iken bir ara tablo bunlarin arasindaki kopruyu kurar ( urun_alim gibi ). Kabaca:
Firmalar:
FirmaID - ana anahtar
Firma Adi
Firma Adresi, telefon ... gibi bilgiler (uzun vadede bu kisim bile baska bir tablo, bir firmanin N tane adresi, telefonu vs olabilir)Urunler:
UrunID - ana anahtar
UrunAdi
Aciklama
SuankiBirimFiyat, StokAdedi (ayni tabloda olabilir baslangicta)UrunAlim: (GelenUrun)
UrunID, FirmaID, GelisTarihi, BirimFiyat, Adet, ...Yani
Firmalar ( 1 ) - ( N ) GelenUrun ( N ) - ( 1 ) Urunler
seklinde iliski var.
Northwind ornegini indir ve ona bak (bu ornek degisik veri tabanlari icin var - SQL server, Access, VFP). O ornekte hem veri tabani var hem de hazir program ornegi.
-
Bu arada, daha once soyledim mi hatirlamiyorum. Veri tabani islemleriyle ugrasacak isen (ya da ugrasmasan bile) bence www.linqpad.net adresinden LinqPad'i indir. Onu kullanarak interaktif kod testleri yaparsin, degisik veritabanlarina baglanirsin vs. C#,VB,F#,SQL,eSQL destegi var icinde.
-
levent_öztürk selamlar,
Konu ile ilgili gelişmeleri paylaşabilir misiniz? Herhangi bir sonuç alabildiniz mi?
İyi çalışmalar,
Emre Günertürk, MSFT
Microsoft bu servisi kullanıcılarına teknik destek verme,Microsoft ürünleri ve teknolojileriyle ilgili bilgi bankasını genişletme amacıyla ücretsiz sunmaktadır.
Bu içerik olduğu gibi benim tarafımdan hazırlanmış olup Microsoft tarafından herhangi gibi bir sorumluluk üstlenildiği anlamına gelmez.
Facebook üzerinden takip et!
Twitter üzerinden takip et!
-
Emre Bey Merhaba,
Aslında tam bir çözüme ulaşamadım. Arkadaşlar bana burada detaylı bir şekilde kodları yazdı anlattılar fakat ben yapamadım.
CetinBasoz , Ne yaparsan yap ama aşağıdaki şekilde sorgu kullanma mutlaka parametre kullanmamı önerdi ama yapamadım.
(CommandText = "Select * From Firmalar Where Unvan ='" & txtfirmaara.Text & "' And Sehir ='" & txtşehirara.Text & "'" ) Projemin yarım halini bu linkte paylaşıyorum acces veritabanı bin klasörünün içerisinde
" http://cid-a3ca9c7a87cd619b.office.live.com/self.aspx/.Documents/StokTakip.rar "
Örneğin aşağıdaki kod bloğunda parametre kullanmam gerekir sanırım ama nasıl yapacağım çözemedim tam olarak.
Aşağıdaki kod bloğu Firmalar formunda ilgili checkboxlar seçildiği takdirde (Unvan ve Şehir ) kriterine göre verileri datagridviewde listeliyor. Ama parametre kullanarak yapamadım.
If TxtFirmaAdı.Checked = True And TxtŞehirAdı.Checked = True Then
cmd.CommandText = "Select * From Firmalar Where Unvan ='" & txtfirmaara.Text & "' And Sehir ='" & txtşehirara.Text & "'"
adap = New OleDbDataAdapter(cmd)
dt = New DataSet
adap.Fill(dt, "Firmalar")
BindingSource1.DataSource = dt
BindingSource1.DataMember = dt.Tables(0).TableName
DataGridView1.DataSource = BindingSource1
ElseIf TxtFirmaAdı.Checked = True Then
cmd.CommandText = "Select * From Firmalar Where Unvan ='" & txtfirmaara.Text & "'"
adap = New OleDbDataAdapter(cmd)
dt = New DataSet
adap.Fill(dt, "Firmalar")
BindingSource1.DataSource = dt
BindingSource1.DataMember = dt.Tables(0).TableName
DataGridView1.DataSource = BindingSource1
ElseIf TxtŞehirAdı.Checked = True Then
cmd.CommandText = "Select * From Firmalar Where Sehir ='" & txtşehirara.Text & "'"
cmd.Parameters.Add("Sehir", OleDbType.VarChar).Value = txtşehirara.Text
adap = New OleDbDataAdapter(cmd)
dt = New DataSet
adap.Fill(dt, "Firmalar")
BindingSource1.DataSource = dt
BindingSource1.DataMember = dt.Tables(0).TableName
DataGridView1.DataSource = BindingSource1
End If
Sizden ricam ekte belirtmiş olduğum projemi inceledikten sonra bu kodlar üzerinde değişiklik yaparak sorguyu parametreli hale getirmemde yardımcı olurmusunuz?
Syg.
-
Bu seninkinin parametreli hali:
If TxtFirmaAdı.Checked = True And TxtŞehirAdı.Checked = True Then cmd.CommandText = "Select * From Firmalar Where Unvan = @unvan And Sehir = @sehir" ElseIf TxtFirmaAdı.Checked = True Then cmd.CommandText = "Select * From Firmalar Where Unvan = @unvan" ElseIf TxtŞehirAdı.Checked = True Then cmd.CommandText = "Select * From Firmalar Where Sehir = @sehir" Else cmd.CommandText = "Select * From Firmalar" End If cmd.Parameters.AddWithValue("@unvan", txtfirmaara.Text) cmd.Parameters.AddWithValue("@sehir", txtşehir.Text) adap = New OleDbDataAdapter(cmd) dt = New DataSet adap.Fill(dt, "Firmalar") BindingSource1.DataSource = dt BindingSource1.DataMember = dt.Tables(0).TableName DataGridView1.DataSource = BindingSource1
Bu da onun yerine Linq kullanan sekli (tam aynisi degil - ornegin K yazarak K ile baslayanlar. Digerinde bilemedim Access oldugu icin - Accessin dilini anlamak muamma)
Dim sorgu As DataView Dim unvan As String = txtfirmaara.Text.ToUpper(New CultureInfo("tr-TR")) Dim sehir As String = txtşehirara.Text.ToUpper(New CultureInfo("tr-TR")) If (TxtFirmaAdı.Checked And TxtŞehirAdı.Checked) Then sorgu = (From kayit In dt.Tables("Firmalar") Where kayit.Field(Of String)("Unvan").ToUpper(New CultureInfo("tr-TR")).StartsWith(unvan) AndAlso kayit.Field(Of String)("Sehir").ToUpper(New CultureInfo("tr-TR")).StartsWith(sehir) Select kayit).AsDataView() ElseIf TxtFirmaAdı.Checked Then sorgu = (From kayit In dt.Tables("Firmalar") Where kayit.Field(Of String)("Unvan").ToUpper(New CultureInfo("tr-TR")).StartsWith(unvan) Select kayit).AsDataView() ElseIf TxtŞehirAdı.Checked Then sorgu = (From kayit In dt.Tables("Firmalar") Where kayit.Field(Of String)("Sehir").ToUpper(New CultureInfo("tr-TR")).StartsWith(sehir) Select kayit).AsDataView() Else sorgu = (From kayit In dt.Tables("Firmalar") Select kayit).AsDataView() End If BindingSource1.DataSource = sorgu
Tabii Linq ve DataSet tirmalamak demek. Dataset olmasa daha iyi. Ancak kafan karismasin, kodun zaten gidecek cok yolu var (mesela public kullanma, tekrarlari onle vs), hepsini hemen ogrenmeye calisma:)
Not: VB gercekten cok zormus. Bundan sonra grekirse C# ile cevap vermeyi tercih ediyorum.
- Yanıt Olarak İşaretleyen Emre GunerturkModerator 28 Kasım 2010 Pazar 19:56
-
Merhaba CetinBazoz,
Öncelikle size tşk.Ederim sabırla bana yardımcı olmaya çalıştığınız için:)
Yazmış olduğunuz kodlar işimi görecektir bundan eminim. Konu ile ilgili başka problemler çıkar ise farklı başlık altında sizinle paylaşacağım.
(mesela public kullanma, tekrarlari onle vs) Ben değişkenlerimi bir modül içerisinde tanımlıyorum. Örnek ( Public dt as Dataset ) ve bunuda projenin heryerinde kullanıyorum. Tekrarları önle den kastınız ben tanımlamış olduğum bu dataseti sadece bir yerde kullanayım.( Firmalar Formum da) Siparişler formuma da Yeni bir dataset tanımlamam gerekir ( Dim dt As dataset ) Doğru mu anlamışım.Aslında bende yeni olduğum için C# ile başlayacaktım ama epey zaman önce vb 6.0 üzerinde biraz yoğunlaşmıştım.O yüzden vb.net ile ilerlemeyi daha uygun gördüm kendime:) Benim yazılımcı düşüncesine sahip olabilmem için ve mantığı tam anlayabilmem için vb.net ' i öğrenmem gerekir sanırım. Tabi ilk önce Algoritma yı öğrenmem gerekir.
Size ve yardımcı olan diğer arkadaşlara çok tşk.ederim.
Syg.
-