Excel'den veri okuma

Excel'i veritabanı olarak kullanmak mümkün.

Aramızda Excel'i kullanmayan yoktur.

Günlük işlerimizi bilgisayar başında yaparken illa ki ucundan kıyısından Excel'e bulaşmışsınızdır.

Excel'i, .NET projelerinde veritabanı olarak kullanabileceğinizi biliyor muydunuz?

Bunun için bize lazım olan ilk şey, güzel bir Connection String.

http://www.daltinkurt.com/Connection-Strings.aspx adresinden Connection String bilgilerine ulaşabilirsiniz.

Ben sitedeki bütün örnekleri ASP.NET üzerinden verdiğim için aşağıdaki örnekleri de aynı şekilde ASP.NET için vereceğim.

İsteyenler kendilerine uyarlayabilirler.

string dosya = "~/App_Data/Veriler.xlsx";
string connString = 
string.Format(@"Provider=Microsoft.ACE.OLEDB.12.0;Data Source={0};Extended Properties=Excel 12.0", Server.MapPath(dosya));

Bu stringi yazmaya çalışmayın. Direkt olarak kopyala-yapıştırı kullanın, zira aradaki bir tek boşluk / küçük-büyük harf bile önemli.

Dosyamız gördüğünüz üzere Excel 2007 / 2010 formatında. 2003 kullanan arkadaşlar (2012'deyiz ^_^) yukarıda verdiğim linke göz atmalıdırlar.

Sıra geldi Excel sayfamızı oluşturmaya. Hemen kafanıza göre bir dosya oluşturabilirsiniz.

  • Çalışma sayfamızın adı, tablomuzun adı (table),
  • En üst satırdaki başlıklar, sütunlarımız (Columns),
  • Gerisi de verilerin bulunduğu satırlarımız (Rows) oluyor.

SqlServer'a bağlanırken SqlConnection, SqlCommand, SqlDataAdapter, vd.,

MySql'e bağlanırken, MySqlConnection, MySqlCommand, MySqlDataAdapter, vd. nasıl kullanıyorsak,

Exel'e bağlanmak için de OleDbConnection, OleDbCommand, OleDbDataAdapter, vd. kullanıyoruz.

Örnek kodu inceleyiniz:

string dosya = "~/App_Data/Ogrenciler.xlsx";
string connString = string.Format(@"Provider=Microsoft.ACE.OLEDB.12.0;Data Source={0};Extended Properties=Excel 12.0;",
    Server.MapPath(dosya));

OleDbConnection conn = new OleDbConnection(connString);
conn.Open();
OleDbCommand cmd = new OleDbCommand("SELECT * FROM [Sayfa1$]", conn);
OleDbDataAdapter da = new OleDbDataAdapter();
da.SelectCommand = cmd;
DataTable dt = new DataTable();
da.Fill(dt);

gv.DataSource = dt;
gv.DataBind();

Çıktı:

 

SqlServer'dan ve MySql'den tek farkı Connection Stringin ve sınıf isimlerinin değişmesi, gerisi gördüğünüz gibi aynı. :)

Şimdi gelelim detaylara:

1. Yukarıda da bahsettiğim gibi bu Excel 2007 / 2010 için geçerli. Eğer Excel 2003 (2012 yılında olduğumuzu tekrar hatırlatırım) kullanıyorsanız, connection stringi değiştirmeniz yeterli olacaktır.

2. Eğer çalıştırdığınız bilgisayarda, Office 2007 / 2010 yüklü ise kodun sorunsuz çalıştığını göreceksiniz. Ama ya Office kurulu olmayan bir bilgisayarda nasıl olacak?

Bu noktada söylemem gerekir ki; sitenizi host ettiğiniz serverda Office'in kurulu olmasını bekleyemezsiniz.

Bu durumda servera (nasıl yaparsınız bilmiyorum, ama hosting firması ile görüşmeniz gerekir) bir program kurmanız gerekiyor.

Microsoft Access Database Engine 2010 (Office 2010 için)

2007 Office System Driver: Data Connectivity Components (Office 2007 için)

3. Excel'den veriyi çekerken, DataAdapter'i kullanarak verileri DataTable'a aktardık, GridView'in DataSource'una bağladık.

Bu kodlar eskidi :)

Artık LINQ var.

Aşağıdaki kodu inceleyiniz:

var ogrenciler = from o in dt.AsEnumerable()
                 select new
                 {
                     SiraNo = o.Field<double>("Sıra No"),
                     Numara = o.Field<double>("Numara"),
                     AdSoyad = o.Field<string>("Adı Soyadı"),
                     Y1 = o.Field<double>("Y1"),
                     Y2 = o.Field<double>("Y2"),
                     S1 = o.Field<double>("S1"),
                     Ortalama = o.Field<double>("Ortalama")
                 };

//   Sınıf ortalaması
var ort = ogrenciler.Average(x => x.Ortalama);

// Y1'den en yüksek alan öğrenci
var ogr = (from o in ogrenciler
           where o.Y1 == ogrenciler.Max(x => x.Y1)
           select o).First();

//Y1-Y2 ortalaması en yüksek ilk 3 öğrenci:
var ogr2 = (from o in ogrenciler.AsEnumerable()
            let ortalama = (o.Y1 + o.Y2) / 2
            orderby ortalama descending
            select o).Take(3);

LINQ ifadelerini DataTable üzerinde kullanmak için DataTableIEnumerable interface'ini destekleyen bir tipe dönüştürdük, sonra da sorgularımızı rahatlıkla yazabildik.

BİLGİ: Bunun için de dt'nin sonuna .AsEnumerable() ekledik. dt den sonra . (nokta) ya basınca bu genişletme metodunu göremiyorsanız, Add Reference'tan .NET sekmesi altında System.Data.DataSetExtensions u bulup ekleyin.

İKAZ: Ben bir uygulamada, (Entity Framework ve LINQ kullandığım bir uygulamada) localhost'ta sorunsuz çalıştırırken, hosta attığımda bir hata mesajı aldım. Çözüm olarak da bu sefer ayrıca bir de System.Data.Entity de referans olarak ekledim, sorun çözüldü.

DİKKAT: Excel'den bilgileri okurken, sayıların double, metinlerin de string olarak geldiğine dikkat edin!

Örnek uygulama için buraya tıklayınız.

Herkese kolay gelsin.