我正在使用房利美抵押貸款資料試驗 MySQL 和資料分析。為此,我創建了兩個表(“perf”和“acq”)和幾個 python 函式。我首先洗掉集合和表(如果存在),然后創建集合(mortgage_analysis)和兩個表。然后我建立一個檔案串列,這些檔案對應于我想要執行的分析年數。所有這些都很好。
然后,我使用以下函式將表格中的資料加載到來自房利美的 perf 和 acq 文本檔案中。相同的函式用于加載兩個表。它每次都與“perf”表一起作業,而從不與“acq”表一起作業。如果我獲取 SQL 陳述句并在 mySQL 作業臺中執行它們,則這些陳述句每次都有效。我很難過,可以使用一些幫助。
在作業臺中有效但在 Python 中無效的 SQL 陳述句是:
LOAD DATA INFILE '/Users/<my user name>/github/mortgage-analysis-example/data/text/acq/Acquisition_2000Q1.txt'
INTO TABLE acq
FIELDS TERMINATED BY '|'
LINES TERMINATED BY '\n'
(loan_id, orig_channel, seller_name, orig_interest_rate, orig_upb, orig_loan_term,
orig_date, first_pay_date, orig_ltv, orig_cltv, num_borrowers, dti,
borrower_credit_score, first_home_buyer, loan_purpose, property_type, num_units,
occupancy_status, property_state, zip, mortgage_insurance_percent, product_type,
coborrow_credit_score, mortgage_insurance_type, relocation_mortgage_ind);
加載這個的python函式是:
def loadTable(env_in, template, file_list):
# env_in: (i know, uck global variable, holds info for this notebook common to all functions
# template: SQL template file
# file_list: python list element with fully qualified file names to use with SQL statement
env = env_in # environment info
from mysql.connector import Error
_file = open(env["base_path"] env["path_separator"] template, "r")
_template = _file.readlines()
try:
conn = mysql.connector.connect(host=env["mySQL"]["host"],user=env["mySQL"]["user"], passwd=env['pw'])
if conn.is_connected():
print('Connected to MySQL database')
except Error as e:
print(e)
cursor = conn.cursor()
cursor.execute("USE mortgage_analysis;")
cursor.execute("SET SESSION sql_mode = '';")
print("starting table load")
t0 = time.time()
res = []
for _file in file_list:
_sql = _template[0].format(_file)
print(f"\n{_sql}\n")
try:
res = cursor.execute(_sql)
warn = cursor.fetchwarnings()
#print(f"warn: {warn}")
except Error as e:
print(f"{_sql} \n{e}")
t1 = time.time()
print(f"Years: {env['years']} Table load time: {t1-t0}")
conn.close
return env
沒有發現錯誤(try 總是有效),也沒有產生警告(fetchwarnings 總是空的)。
用于創建這兩個表的 SQL 陳述句是:
DROP TABLE IF EXISTS acq;
CREATE TABLE acq (id DOUBLE AUTO_INCREMENT, loan_id DOUBLE, orig_channel VARCHAR(255), seller_name VARCHAR(255), orig_interest_rate DOUBLE, orig_upb DOUBLE, orig_loan_term DOUBLE, orig_date VARCHAR(255), first_pay_date VARCHAR(255), orig_ltv DOUBLE, orig_cltv DOUBLE, num_borrowers DOUBLE, dti DOUBLE, borrower_credit_score DOUBLE, first_home_buyer VARCHAR(255), loan_purpose VARCHAR(255), property_type VARCHAR(255), num_units DOUBLE, occupancy_status VARCHAR(255), property_state VARCHAR(255), zip DOUBLE, mortgage_insurance_percent DOUBLE, product_type VARCHAR(255), coborrow_credit_score DOUBLE, mortgage_insurance_type DOUBLE, relocation_mortgage_ind VARCHAR(255), PRIMARY KEY (id));
DROP TABLE IF EXISTS perf;
CREATE TABLE perf (id DOUBLE AUTO_INCREMENT, loan_id DOUBLE, monthly_reporting_period VARCHAR(255), servicer VARCHAR(255), interest_rate DECIMAL(6,3), current_actual_upb DECIMAL(12,2), loan_age DOUBLE, remaining_months_to_legal_maturity DOUBLE, adj_remaining_months_to_maturity DOUBLE, maturity_date VARCHAR(255), msa DOUBLE, current_loan_delinquency_status DOUBLE, mod_flag VARCHAR(255), zero_balance_code VARCHAR(255), zero_balance_effective_date VARCHAR(255), last_paid_installment_date VARCHAR(255), foreclosed_after VARCHAR(255), disposition_date VARCHAR(255), foreclosure_costs DOUBLE, prop_preservation_and_reair_costs DOUBLE, asset_recovery_costs DOUBLE, misc_holding_expenses DOUBLE, holding_taxes DOUBLE, net_sale_proceeds DOUBLE, credit_enhancement_proceeds DOUBLE, repurchase_make_whole_proceeds DOUBLE, other_foreclosure_proceeds DOUBLE, non_interest_bearing_upb DOUBLE, principal_forgiveness_upb VARCHAR(255), repurchase_make_whole_proceeds_flag VARCHAR(255), foreclosure_principal_write_off_amount VARCHAR(255), servicing_activity_indicator VARCHAR(255), PRIMARY KEY (id));
uj5u.com熱心網友回復:
我測驗了代碼,我必須進行一些更改才能使其正常作業。
不要改變sql_mode。我沒有收到任何錯誤,我能夠在不影響 sql_mode 的情況下加載資料。
我使用了測驗資料:
1|2|name1|3|4|4|date|date|5|6|7|8|9|buyer|purpose|type|10|status|state|11|12|type|13|14|ind
1|2|name2|3|4|4|date|date|5|6|7|8|9|buyer|purpose|type|10|status|state|11|12|type|13|14|ind
我敦促您選擇更合適的資料型別。您應該在 MySQL 中幾乎從不使用 FLOAT 或 DOUBLE,除非您要存盤科學測量值或其他東西。絕對不是貨幣單位或整數。
我不會使用 VARCHAR 來存盤日期。MySQL 有 DATE 和 DATETIME,它們確保日期格式正確,因此您可以進行比較、排序、日期算術等。
如果您有錯誤提示您應該放寬 sql_mode 并允許無效查詢或無效資料,我建議您改為修復資料。即使您加載了資料,如果您允許非嚴格的 SQL 模式,也有可能成為垃圾。
代碼更改:
我沒有使用format()嘗試將檔案名插入到查詢模板中,而是使用了查詢引數。洗掉帶有 的行_template[0].format(_file),改為使用:
res = cursor.execute(_template, [_file])
但是模板必須在不帶引號的情況下放置占位符:
正確的:
LOAD DATA INFILE %s INTO TABLE...
不正確:
LOAD DATA INFILE '%s' INTO TABLE...
最后,默認情況下不提交 Python 中的資料更改。也就是說,您可以插入資料,然后在使用時conn.close將未提交的更改丟棄。所以我加了一行:
conn.commit()
try/catch我在執行 SQL 后將其放入塊中。
這樣就成功加載了資料。請注意,我必須對您的輸入資料做出假設,因為您沒有共享樣本。我不知道您的檔案是否實際上具有正確的欄位分隔符和行分隔符。但我認為它是,因為你說它在 MySQL Workbench 中作業。
轉載請註明出處,本文鏈接:https://www.uj5u.com/qiye/464317.html
