import txt do bazy SQL

0

Witam,
Zamierzam stworzyć bardzo prosty słownik angielsko-polski(polsko-anielski) na PalmTopa.
Moja baza słówek to plik txt zawierający 120.000 linii - w postaci naprzemiennej: slowo ANG i słowo POL:
(czyli 60 000 słówek) przykład pliku:
"
a certain
jaki
a freak of nature
wybryk natury
a year ago
rok temu
A.D.
Roku Pańskiego
a.m.
przed południem, rano
A.M.
przed południem, rano
aback
być zaskoczonym
abacus
abakus
abacuses
abakusy
...
...
"
Chcę napisać jakiś prosty skrypt w C# , albo skorzystać z VS 2005 PE + MS SQL SERWER 2005
który by importował plik do prostej bazy o strukturze: ID------ANG------POL

moje pytania to:

1 - Jak zacząć,jak to ugryźć,jakieś hasła, jakich klas szukać w dokumentacji (C#), czy VS2005 jest tak wspaniały że obejdzie się pisania skryptu i wystarczy tylko klikanie ?

2 - Gdzie implementować dane, od razu do SQL SERWER CE (baza PalmTop) czy najpier do SQL SERWER 2005 PE a potem do SQL CE?

3 - Co zrobić żeby były polskie literki (ą i ś )

Dziękuje serdecznie [browar] za wszelką pomoc :-)

0
kiniu napisał(a)

1 - Jak zacząć,jak to ugryźć,jakieś hasła, jakich klas szukać w dokumentacji (C#), czy VS2005 jest tak wspaniały że obejdzie się pisania skryptu i wystarczy tylko klikanie ?

Jasne. Wystarczy uruchomić VS 2005 Command Prompt, wkleić treść posta i wcisnąć ENTER, w katalogu C:/bin utworzy się żądany program :P

To moja propozycja:
Co do odczytu z pliku: FileStream i StreamReader, jeśli chcesz czytać linia po linii to metoda ReadLine, jeśli cały plik na raz, to ReadToEnd.
Dzielenie wiersza przy użyciu String.Split
Zapis do bazy - SqlCommand, jego właściwości CommandText i Connection, metoda ExecuteNonQuery, oczywiście przy otwartym połączeniu do bazy.

Na przykład tak, bo metod rozwiązania tego są pewno miliony.

Co do polskich znaków - obstawiam użycie typu nvarchar dla kolumn w bazie.

A co do dokumentacji: <url>www.msdn.com</url>

0

Jasne. Wystarczy uruchomić VS 2005 Command Prompt, wkleić treść posta i wcisnąć ENTER, w katalogu C:/bin utworzy się żądany program :P

iii .. jasne ;-)

To moja propozycja:
Co do odczytu z pliku: FileStream i StreamReader, jeśli chcesz czytać linia po linii to metoda ReadLine, jeśli cały plik na raz, to ReadToEnd.Dzielenie wiersza przy użyciu String.Split

Właśnie to wszystko już zrobiłem, i efektem jest właśnie taki pliczek txt, ładnie poukładane słówka po kolei :-)

Zapis do bazy - SqlCommand, jego właściwości CommandText i Connection, metoda ExecuteNonQuery, oczywiście przy otwartym połączeniu do bazy.

Właśnie o to pytałem - na razie umiem wprowadzić dane do tabeli (przy otwartym połączeniu)

0

Nie zrozumiales odpowiedzi @somekind.

StreamReader reader = File.OpenText("dane.txt");
String pl = "";
String en = "";
while(pl != null && en != null)
{
  SqlCommand command = new SqlCommand("insert into tabela (pl, eng) values(@pl, @eng)", polaczenie);
  command.Parameters.Add("@pl", SqlDbType.NVarChar);
  command.Parameters.Add("@en", SqlDbType.NVarChar);
  en = reader.ReadLine()
  pl = reader.ReadLine()
  if(pl != null && en != null)
  {
    command.Parameters["@en"] = en;
    command.Parameters["@pl"] = pl;
    command.ExecuteNonQuery();
  }
}
  1. Obojetne, jak masz juz zaimportowane do bazy to latwiej przenosic.
  2. Jesli w pliku jest kodowanie utf-8 to tak sie zaimportuje. Pozniej zalezy gdzie i jak bedziesz wyswietlal, ale nie powinno byc problemu.

PS. Kod pisany z palca, moze zawierac literowki, za wszelkie zniszczenia nim powodowane odpowiada kompilujacy ;)

0

;] patrze na ten kod ..i jakbym czytał książkę i wydaje mi się to takie proste..

mam wrażenie jakbym znał słowa , tylko sam nie umiałbym złożyć ich w zdania ;]

Dzięki Wielkie Johny Bravo [!!!]

  1. Jesli w pliku jest kodowanie utf-8 to tak sie zaimportuje. Pozniej zalezy gdzie i jak bedziesz wyswietlal, ale nie powinno byc problemu.

nie wiem jakie jest kodowanie w pliku, w poprzednim pliku z którego sortowaliśmy regexem wszystkie polskie znaki były zmienione na znak zapytania, jednak odczytywałem z pliku za pomocą :
File.ReadAllText("ang_pol.txt", System.Text.Encoding.GetEncoding("iso-8859-2"))
i poukładany plik stworzył z polskimi słówkami po za słówkami "ś" i "ą "
</quote>

0

A jakie jest oryginalne kodowanie pliku? I po co przerabiasz na ISO? Notepad nie odczytuje poprawnie ani iso ani utf8, wiec nim nie sprawdzisz czy dobrze zapisalo.

0
johny_bravo napisał(a)

A jakie jest oryginalne kodowanie pliku? I po co przerabiasz na ISO? Notepad nie odczytuje poprawnie ani iso ani utf8, wiec nim nie sprawdzisz czy dobrze zapisalo.

Oryginalne kodowanie to ASCII, zarówno notepad jak i notepad ++ bez przerobienia na ISO nie radzi sobie z
wszystkimi polskimi literami, a po przerobieniu na ISO nie radzi sonie tylko z ś i ą. A czym najlepiej sprawdzić (zresztą będę się martwić jak po i mporcie do bazy wyskoczą krzaczki.

0

ANSII, nie ASCII jezeli juz, czy windows-1250. Zapisz w takim samym kodowaniu albo w utf8 i tez bedzie dobrze.

0

command.Parameters["@eng"] = ANG;

wywala: cannot implicitli convert type'string' to 'system.data.sqlclient.sqlparameter'

0

problem jest chyba jednak troche wczesniej..
command.Parameters.Add("@pl",SqlDbType.NVarChar);

..oczekuje na parametr "@pl" ale jest nie otrzymuje..

" The parameterized query'<@pl varchar <8000> insert into slownik <POL> values <@pl>' expects the parameter '@pl',which was not supplied"

0
  SqlCommand command = new SqlCommand("insert into tabela (pl, eng) values(@pl, @en)", polaczenie);
  en = reader.ReadLine()
  pl = reader.ReadLine()
  if(pl != null && en != null)
  {
    SqlParameter param = new SqlParameter("@pl", SqlDbType.NVarChar);
    param.Value = pl;
    command.Parameters.Add(param);
    SqlParameter param = new SqlParameter("@en", SqlDbType.NVarChar);
    param.Value = en;
    command.Parameters.Add(param);
    command.ExecuteNonQuery();
  }
0

Czemu nie mogę zmieniać właściwości kolumn z pozycji VS2005, podczas gdy baza tworzona była za pomocą Management Studio?

0

Chcesz zmieniać typy kolumn tabel w bazie danych w kodzie programu? Bo nie rozumiem...

0

Chcę zmienić właściwości kolumny tabeli w bazie danych klikając na zakładkę " properties " np. "Nullable" zmienić na FALSE. Niestety wszystkie właściwości są tak jakby na stałe..czy można je jakoś zmieniać, czy tylko jest t o możliwe w Management Studio ?

0

Johny, niestety nie doszedłem jeszcze do tego jak poprawnie wykorzystać twój kod. Poniższe linijki powodują że do kolumny pol wstawiane jest 213 tys znaczków @pl oraz do kolumny ang około 13.5 tys znaczków @eng

using System;
using System.Collections.Generic;
using System.Text;
using System.Data.SqlClient;
using System.Data;
using System.IO;

namespace baza
{
    class WczytajDoSql
    {
        static void Main(string[] args)
        {
            SqlConnection myCn = new SqlConnection("Data Source=(local)\\sqlexpress;Initial Catalog=slownik;Integrated Security=SSPI");
            myCn.Open();
            Console.WriteLine("Połączono z Bazą Danych ");
            StreamReader reader = File.OpenText("pliczek0.txt");
            String pol = "";
            String eng = "";

            while (eng != null && pol != null)
            {

                SqlCommand command = new SqlCommand("insert into baza (pol,ang) values ('@pl','@eng') ", myCn);
                pol = reader.ReadLine();
                eng = reader.ReadLine();




                SqlParameter paramEn = new SqlParameter("@eng", SqlDbType.NVarChar);
                paramEn.IsNullable = true;
                paramEn.Direction = ParameterDirection.Output;
                paramEn.Size = 88;
                paramEn.Value = eng;
                command.Parameters.Add(paramEn);

                SqlParameter paramPl = new SqlParameter("@pl", SqlDbType.NVarChar);
                paramPl.IsNullable = true;
                paramPl.Direction = ParameterDirection.Output;
                paramPl.Size = 88;
                paramPl.Value = pol;
                command.Parameters.Add(paramPl);

                command.ExecuteNonQuery();

            }


  

                SqlDataAdapter dabaza = new SqlDataAdapter("Select * from baza", myCn);
                DataSet dsSlownik = new DataSet("slownik");
                dabaza.MissingSchemaAction = MissingSchemaAction.AddWithKey;
                dabaza.Fill(dsSlownik, "baza");
                DataTable tblbaza;
                tblbaza = dsSlownik.Tables["baza"];


                Console.Write("{0,0}", "POL");
                Console.Write("{0,10}", "ANG");
                Console.Write("{0,8}", "ID");
                Console.WriteLine();

                foreach (DataRow drCurrent in tblbaza.Rows)
                {
                    Console.WriteLine("{0}{1}{2}", drCurrent["ANG"].ToString(),
                                                  drCurrent["POL"].ToString(),
                                                  drCurrent["ID"].ToString());

                }
                Console.ReadLine();

   }
 }
}

3:27 .. za kilka godzin do pracy :-) to się nazywa pasja :>

0

U Ciebie:

paramEn.Value = "@eng";

u mnie:

param.Value = en;
0

zły kod wkleiłem, już poprawiłem (kombinowałem z kodem na różne sposoby)

Ale niestety to nie jest ten problem.

0

Po co to?

paramEn.IsNullable = true;
paramEn.Direction = ParameterDirection.Output;
paramEn.Size = 88;
0

bez tego sie nie kompiluje, wyskakuje to samo co na początku :
..oczekuje na parametr "@pl" ale jest nie otrzymuje..

" The parameterized query'<@pl varchar <8000> insert into slownik <POL> values <@pl>' expects the parameter '@pl',which was not supplied"

co prawda tego nie musi być..paramEn.IsNullable = true; ale to chyba dlatego ze zmieniłem właściwości kolumn, teraz mogą przyjmować wartości null

0

Najpierw:
SqlConnection myCn = new SqlConnection("Data Source=(local)\sqlexpress;Initial Catalog=slownik;Integrated Security=SSPI");

Później:
<code class="c#">SqlCommand command = new SqlCommand("insert into baza (pol,ang) values ('@pl','@eng') ", myCn);

To jak w końcu nazywa sie Twoja tabela? "slownik" czy "baza"?

Co do tego:

paramEn.Direction = ParameterDirection.Output;
paramEn.Size = 88;

Dlaczego, gdy chcesz coś "wrzucić" do bazy, ustawiasz kierunek parametru na wyjściowy?
Druga uwaga - jesteś pewien, że nie masz zwrotów dłuższych niż 88 znaków?

Dlaczego nie otwierasz i nie zamykasz połączenia do bazy? Można tak w ogóle?

Ja bym to napisał tak:

<code class="c#">
while (eng != null && pol != null)
{
    pol = reader.ReadLine();
    eng = reader.ReadLine();
    SqlCommand command = new SqlCommand("insert into baza (pol,ang) values ('@pl','@eng') ", myCn);
    command.Parameters[@pl].SqlDbType = SqlDbType.NVarChar;
    command.Parameters[@eng].SqlDbType = SqlDbType.NVarChar;
    command.Parameters[@pl].Value = pol;
    command.Parameters[@eng].Value = eng;
    try
    {
        command.Connection.Open();
        command.ExecuteNonQuery();        
    }
    catch(Exception ex)
    {
        throw ex;
    }
    finally
    {
        command.Connection.Close();
    }
}

Pobieranie danych z bazy też możesz zrobić bez adaptera i datasetu, wystarczy sqldatareader i datatable.

0

To jak w końcu nazywa sie Twoja tabela? "slownik" czy "baza"?

Baza nazywa się "slownik" a tabela nazywa się "baza"

ta linijka sie nie kompiluje:

command.Parameters[@pl].SqlDbType = SqlDbType.NVarChar;

komunikat: "The name 'pl' does not exist in the current context"

musialem zmienic nazwe parametru z "[@pl]" na "[@pol]", teraz sie kompiluje ale i tak nie zapisuje do bazy danych, mysle ze juz jest bardzo blisko od zapisania danych, komunikat o bledzie zawiera pierwsze slowko z listy..a nie jak wczesniej tylko nazwe parametru

"System.Index.OutOfRangeException: An SqlParameter with ParameterName ' a certain' is not contained by this SqlParameterCollection."

0
somekind napisał(a)

To jak w końcu nazywa sie Twoja tabela? "slownik" czy "baza"?

Przepraszam, tego pytania nie było, powaliło mi się. I nie śmiejcie się, już się sam zbiczowałem.

kiniu napisał(a)

Baza nazywa się "slownik" a tabela nazywa się "baza"

No właśnie bardzo ekscentryczny pomysł, aby nazwać tabelę "baza".</quote>

kiniu napisał(a)

komunikat: "The name 'pl' does not exist in the current context" :-(

Spróbuj:
command.Parameters["pl"].SqlDbType = SqlDbType.NVarChar;

0

command.Parameters["pl"].SqlDbType = SqlDbType.NVarChar;

tez nie..szukam w dokumentacji tego sposobu i nie moge znaleźć

"System.Index.OutOfRangeException: An SqlParameter with ParameterName ' pl' is not contained by this SqlParameterCollection."

0

Jak juz to

command.Parameters["@pl"].SqlDbType = SqlDbType.NVarChar;

Jak bede mial jutro czas to napisze dzialajacy przyklad (z kompilatorem w reku i w ogole ;P ) Sadzilem, ze wystarczy koncepcja, zebys sobie poradzil, ale widze, ze coraz bardziej bladzisz na manowce.
@somekind: zamykanie i otwieranie polaczenia to sredni pomysl, bo:

  1. wydluza czas dzialania petli
  2. .net chyba i tak nie zamyka polaczenia od razu, bo standardowo dziala connection pooling.
0
johny_bravo napisał(a)

Jak bede mial jutro czas to napisze dzialajacy przyklad (z kompilatorem w reku i w ogole ;P ) Sadzilem, ze wystarczy koncepcja, zebys sobie poradzil, ale widze, ze coraz bardziej bladzisz na manowce.

Akurat ja miałem:

static void Main(string[] args)
{
string ścieżka = Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory) + "/slow.txt";
StreamReader sr = File.OpenText(ścieżka);
string pol = String.Empty;
string ang = String.Empty;

SqlConnection con = new SqlConnection("Server=(local); Initial Catalog=Test2; Integrated Security=true");

SqlCommand inCmd = new SqlCommand("INSERT INTO Slownik (pol, ang) VALUES (@pol, @ang)");
inCmd.Connection = con;
inCmd.Connection.Open();
while ((ang = sr.ReadLine()) != null && (pol = sr.ReadLine()) != null)
{
    inCmd.Parameters.Clear();
    inCmd.Parameters.AddWithValue("@pol", pol);
    inCmd.Parameters.AddWithValue("@ang", ang);
    inCmd.ExecuteNonQuery();
}
inCmd.Connection.Close();

Console.WriteLine("Tabela wypełniona!");
Console.ReadLine();

DataTable dt = new DataTable();

SqlCommand rdrCmd = new SqlCommand("SELECT * FROM Slownik");
rdrCmd.Connection = con;
rdrCmd.Connection.Open();
dt.Load(rdrCmd.ExecuteReader(CommandBehavior.CloseConnection));
Console.WriteLine("id\tpol\tang");
for (int i = 0; i < dt.Rows.Count; i++)
    Console.WriteLine("{0}\t{1}\t{2}", dt.Rows[i][0], dt.Rows[i][1], dt.Rows[i][2]);

Console.WriteLine("\nTabela odczytana!");
Console.ReadLine();

}

Mam nadzieję, że zadowoliłem Cię jednokrotnym otwieraniem połączenia. Pewno jestem jakiś inny, ale bez otwierania nie umiem nic do bazy zapisać :(

P.S. Poprzednia wersja algorytmu nie wykrywała poprawnie końca pliku - załadowywała całą tabelę poprawnie i chciała dalej jechać. (Przynajmniej tak to wyglądało) Dlatego zmodyfikowałem warunek w while.

P.P.S Przepraszam, że do odczytu też otwieram połączenie :(
0

somekind - teraz to przesadziłeś.. godzina- 2:54 ;-)

Mega dzięki za kod, zaraz go sprawdzę [green]

A to moje :>

namespace baza
{
    class WczytajDoSql
    {
        static void Main(string[] args)
        {
            SqlConnection myCn = new SqlConnection("Data Source=(local)\\sqlexpress;Initial  Catalog=slownik;Integrated Security=SSPI");
            StreamReader reader = File.OpenText("pliczek0.txt");
            String pol = "";
            String ang = "";
            
            while (ang != null && pol != null)
            {   //int id =[i]+1 ; 
                //Console.WriteLine(id);
                SqlCommand insert = new SqlCommand("INSERT INTO baza (pol, ang) VALUES (@pol,@ang) ", myCn);
                SqlParameter in1 = new SqlParameter("@pol", SqlDbType.NVarChar);
                pol = reader.ReadLine();
                in1.Value = pol;
                insert.Parameters.Add(in1);

                SqlParameter in2 = new SqlParameter("@ang", SqlDbType.NVarChar);
                ang = reader.ReadLine();
                in2.Value = ang;
                insert.Parameters.Add(in2);

                if (ang != null && pol != null)
                {
                    myCn.Open();

                    insert.ExecuteNonQuery();
                }
                myCn.Close();
             }
         } 
     }
}              

     
0

somekind - twój program działa identycznie jak mój :-) zjada polskie literki i nie potrafi zapisac do bazy w alfabetycznej kolejnosci :|

0
kiniu napisał(a)

nie potrafi zapisac do bazy w alfabetycznej kolejnosci :|

A sortowanie w bazie to co?

0

Johny a kiedy ty niby spales? :-D ..ostatni post przed snem godz. 0:22 - a pierwszy juz z rana 4:44 !

No chyba ze sypiasz w dzien ..a pracujesz w nocy.

A sortowanie w bazie to co?

Rozumiem ze chodzi Tobie o polecenia sortujace w jezyku SQL - to juz powinno byc proste. Ale tak mnie to zastanawia czemu program czytajac linijka po linijce z pliku ktory jest posortowany, i zapisuje te zmienne po kolei w petli do bazy, to jakim prawem wynik zapisania jest nie po kolei :-/

Teraz musze Windows Form w VS wziasc na warsztat..

0

o nie , plik slownik.mdf zajmuje az 12 MB [!!!] :-O czemu tak duzo, kurcze, plik tekstowy mial 380 kilo...
da sie cos z tym zrobic ? przeciez PalmTop ma ze 100 mb pamieci , czy to mozliwe ze jak sie na jakiejs bazie dluo zapisuje i kasuje to ona tak rosnie sztucznie?

1 użytkowników online, w tym zalogowanych: 0, gości: 1