2012-12-21 118 views
4

在一個項目中,我需要從一個Visual FoxPro數據庫中提取數據,該數據庫存儲在dbf文件中,y有一個數據目錄,包含539個需要考慮的文件,每個文件都代表一個數據庫表,所以我一直在做一些測試,我的代碼是這樣的:用pyodbc讀取DBF文件

import pyodbc 

connection = pyodbc.connect("Driver={Microsoft Visual FoxPro Driver};SourceType=DBF;SourceDB=P:\\Data;Exclusive=No;Collate=Machine;NULL=No;DELETED=Yes") 
tables = connection.cursor().tables() 
for _ in tables: 
    print _ 

這僅打印15表,而沒有明顯的模式,總是相同的15個表,我認爲這是因爲休息表是空的,但我查了一下,列表中的一些表(dbf文件)也是空的,然後,我認爲這是一個權限問題,但所有文件具有相同的權限結構,所以我不知道這裏發生了什麼事。

任何光?

編輯: 它不是truccating輸出,表其名單是不是15首或類似的東西

+0

謝謝你驚人的問題和答案!對於任何好奇的人來說,原始問題***中的代碼都可以在32位系統上使用老版本的FoxPro。 –

回答

6

我做到了!!!!

有其中幾個問題我在做什麼,所以,我在這裏跟我做了什麼來解決這個問題

的第一件事是一個驅動程序問題(實現了第一次和Ethan Furman的解決方案之後),它事實證明,Windows的DBF驅動程序是32位程序,並且運行在64位操作系統上,所以我安裝了Python-amd64,這是第一個問題,所以我安裝了一個32位的Python。

第二個問題是庫/文件問題,根據this,VFP> 7中的dbf文件是不同的,所以我的pyodbc庫不會正確讀取它們,所以我嘗試了一些沒有成功的OLE-DB庫,我決定從頭開始。

Google上搜尋了一會兒帶我去this後這終於給了我這個

基本上一盞燈,我所做的是以下幾點:

import win32com.client 

conn = win32com.client.Dispatch('ADODB.Connection') 
db = 'C:\\Profit\\profit_a\\ARMM' 
dsn = 'Provider=VFPOLEDB.1;Data Source=%s' % db 
conn.Open(dsn) 

cmd = win32com.client.Dispatch('ADODB.Command') 
cmd.ActiveConnection = conn 
cmd.CommandText = "Select * from factura, reng_fac where factura.fact_num = reng_fac.fact_num AND factura.fact_num = 6099;" 

rs, total = cmd.Execute() # This returns a tuple: (<RecordSet>, number_of_records) 

while total: 
    for x in xrange(rs.Fields.Count): 
     print '%s --> %s' % (rs.Fields.item(x).Name, rs.Fields.item(x).Value) 
     rs.MoveNext() 
     total = total - 1 

它給了我20條記錄,我檢查與DBFCommander並且是OK

首先,您需要安裝pywin32 extensions(32位)和Visual FoxPro OLE-DB Provider(僅適用於32位),在我的情況下VFP 9.0

另外,很高興在w3c網站上閱讀de ADO Documentation

這對我很有用。非常感謝那些回覆

+0

恭喜!看起來也是使用'win32'的好例子。 –

+0

非常感謝!是的,這樣我就可以利用VFP的SQL容量,所以我不必實現所有的關係代數,我甚至想用dbf包和PLY實現上下文無關語法以「可重用的方式」解決這個問題 – israelord

+0

這太棒了!我嘗試了其他dbf庫,但似乎他們無法獲得正確的輸出,可能是因爲VFP版本不同。我認爲這是使用VFP dbfs的首選解決方案。唯一的缺點是必須安裝win32的所有東西。 – smartexpert

2

我知道這並不直接回答你的問題,但仍可能有幫助。我在使用ODBC與VFP數據庫時遇到了很多問題,並且我發現在可能的情況下將VFP表視爲可用的表更容易。

使用Yusdi Santoso的dbf.py和glob,下面是一些代碼,用於打開目錄中的每個表並遍歷每條記錄。

import glob 
import os 
import dbf 

os.chdir("P:\\data") 
for file in glob.glob("*.dbf"): 
    table = dbf.readDbf(file) 
    for row in table: 
     #do stuff 
+0

這還挺能工作,但你怎麼跟這樣的數據,你如何選擇一些列或發現通過?非常感謝您的回答 – israelord

+0

外鍵關係的數據出來,在類型的字典的名單,如果我還記得工作正確。 '對於表中的行:''data = row ['FIELDNAME']'對於排序,您可以使用運算符來執行諸如'table.sort(key = operator.itemgetter('FIELDNAME'))''。至於外鍵,在這種情況下全是手動的。您正在使用此方法處理表級而不是數據庫級。 – TheSentinel

+0

非常感謝,我試了一下,它的工作原理。如果我無法在數據庫級別找到方法,我會這樣做。 – israelord

2

我會用我自己的dbf package和代碼會去是這樣的:

import dbf 
from glob import glob 

for dbf_file in glob(r'p:\data\*.dbf'): 
    with dbf.Table(dbf_file) as table: 
     for record in table: 
      do_something_with(record) 

表是列表等,通過迭代返回記錄。一個記錄是list-,dict-和obj-like,並且迭代返回值;除了迭代整個記錄之外,還可以通過偏移量(第一個字段爲record[0]),字段名稱類似字典訪問(record['some_field'])或字段名稱使用類似obj.attr的訪問(record.some_field)訪問各個字段。

如果你只是想每個dbf文件的內容轉儲到csv文件,你可以這樣做:

for dbf_file in glob(r'p:\data\*.dbf'): 
    with dbf.Table(dbf_file) as table: 
     dbf.export(table, dbf_file) 
+1

非常有趣和有用,非常感謝,我喜歡csv導出功能,我使用其他dbf工具編碼它。非常感謝你!這爲我節省了一些時間。 – israelord

相關問題