2010-08-18 9 views
6

Obsługuję proces ETL, który przekształca wejściowe pliki płaskie w tabelę bazy danych SqlServer. Kod jest prawie w 100% T-SQL i działa wewnątrz DB. Nie jestem właścicielem kodu i nie mogę zmienić przepływu pracy. Mogę tylko pomóc skonfigurować "tłumaczenie" SQL, który pobiera dane pliku i konwertuje je do danych tabeli (więcej o tym później).Przekształcanie/Przesyłanie nVarChar z separatorem przecinków na dziesiętne

Teraz, klauzule są na uboczu ...

Jeden z naszych dostawców plików niedawno zmienił sposób stanowią one kwotę pieniężną z '12345.67' do '12,345.67'. Nasz SQL, który przekształca wartość, wygląda na SELECT FLOOR(CAST([inputValue] AS DECIMAL(24,10))) i już nie działa. Tj. Przecinek przerywa obsadę.

Biorąc pod uwagę, że mam do przechowywania wartości końcowej jako Decimal (24,10) typu danych (tak, ja sobie sprawy FLOOR wymazuje wszystkie precyzję post-dziesiętny-punktową - projektant nie był zsynchronizowany z klientem), co mogę zrobić skutecznie obsłużyć ten ciąg? "

Dziękuję za Twoje pomysły.

+0

czy któraś z tych odpowiedzi rozwiązała Twój problem? –

+0

@KM: Omawiam teraz te sugestie z naszą grupą DBA. Z mojego punktu widzenia, wspólne podejście zaproponowane (używając Replace()) wydaje się działać. Zaktualizuje się wkrótce. – SethO

Odpowiedz

7

spróbuj REPLACE (Transact-SQL):

SELECT REPLACE('12,345.67',',','') 

WYJŚCIE:

12345.67 

więc byłoby:

SELECT FLOOR(CAST(REPLACE([input value],',','') AS DECIMAL(24,10))) 
+0

+1 ... Zastąp i DZIAŁAJ, aby zachować oryginalną funkcjonalność. – Fosco

1

Działa to dla mnie:

DECLARE @foo NVARCHAR(100) 
SET @foo='12,345.67' 

SELECT FLOOR(CAST(REPLACE(@foo,',','') AS DECIMAL(24,10))) 

Prawdopodobnie jest ważna tylko dla sortowania/kulturze, gdzie przecinek nie jest separator dziesiętny (tj: hiszpański)

+0

Podnosisz dobry punkt, David. Wiem, że niektóre dane pochodzą z Europy i Azji - może to zepsuć wszelkie manipulacje ciągami z przecinkami do pustych ciągów. Będę musiał skontaktować się z klientem w tej sprawie. – SethO

+0

Najlepiej, aby aplikacja wykryła ustawienia narodowe użytkownika, przekonwertuj je na liczbę dziesiętną, a następnie przejdź do serwera sql jako wartość dziesiętna. Problem zniknie. – David

1

SELECT FLOOR (CAST(REPLACE([inputValue], ',', '') AS DECIMAL(24,10)))

2

Choć niekoniecznie jest najlepszym podejściem do mojej sytuacji, chciałem zostawić potencjalne rozwiązanie do wykorzystania w przyszłości, które odkryliśmy podczas badania tego problemu.

Wygląda na to, że typ danych SqlServer MONEY może być używany jako bezpośrednie rzutowanie dla ciągów znaków z przecinkiem oddzielającym część dziesiętną. Więc jeśli SELECT CAST('12,345.56' AS DECIMAL(24,10)) zawiedzie, SELECT CAST('12,345.56' AS MONEY) zakończy się pomyślnie.

Jednym z nich jest to, że typ danych MONEY ma dokładność 4 miejsc po przecinku i wymagałby wyraźnego rzutowania, aby uzyskać go do DECIMAL, jeśli jest to potrzebne.

Powiązane problemy