Oracle
 sql >> Cơ Sở Dữ Liệu >  >> RDS >> Oracle

Không thể đọc đúng bảng SQL trong python:các cột varchar được nhập dưới dạng ký tự / bộ giá trị được phân tách bằng dấu phẩy

Đây có vẻ là sự cố khi sử dụng jaydebeapi với jpype . Tôi có thể tái tạo điều này khi kết nối với Oracle db theo cách giống như cách bạn làm (trong trường hợp của tôi là Oracle 11gR2, nhưng vì bạn đang sử dụng ojdbc8.jar , Tôi đoán nó cũng xảy ra với các phiên bản khác).

Có nhiều cách khác nhau mà bạn có thể giải quyết vấn đề này:

Thay đổi kết nối của bạn

Vì lỗi dường như chỉ xảy ra trong một tổ hợp các gói cụ thể, điều hợp lý nhất cần làm là thử và tránh những điều này và do đó lỗi hoàn toàn.

  1. Cách 1:Sử dụng jaydebeapi không có jpype :

    Như đã lưu ý, tôi chỉ quan sát thấy điều này khi sử dụng jaydebeapi với jpype . Tuy nhiên, trong trường hợp của tôi, jpype là không cần thiết ở tất cả. Tôi có .jar tệp cục bộ và kết nối của tôi hoạt động tốt mà không có nó:

    import jaydebeapi as jdba
    import pandas as pd
    import os
    
    db_host = 'db.host.com'
    db_port = 1521
    db_sid = 'YOURSID'
    
    jar=os.getcwd()+'/ojdbc6.jar'
    
    conn = jdba.connect('oracle.jdbc.driver.OracleDriver', 
                    'jdbc:oracle:thin:@' + db_host + ':' + str(db_port) + ':' + db_sid, 
                    {'user': 'USERNAME', 'password': 'PASSWORD'}, 
                    jar
                    )
    
    df_jay = pd.read_sql('SELECT * FROM YOURSID.table1', conn)
    
    conn.close()
    

    Trong trường hợp của tôi, điều này hoạt động tốt và tạo khung dữ liệu bình thường.

  2. Phương án 2:Sử dụng cx_Oracle thay vào đó:

    Sự cố cũng không xảy ra nếu tôi sử dụng cx_Oracle để kết nối với Oracle db:

    import cx_Oracle
    import pandas as pd
    import os
    
    db_host = 'db.host.com'
    db_port = 1521
    db_sid = 'YOURSID'
    
    dsn_tns = cx_Oracle.makedsn(db_host, db_port, db_sid)
    cx_conn = cx_Oracle.connect('USERNAME', 'PASSWORD', dsn_tns)
    
    df_cxo = pd.read_sql('SELECT * FROM YOURSID.table1', con=cx_conn)
    
    cx_conn.close()
    

    Lưu ý:Đối với cx_Oracle để hoạt động, bạn phải có Ứng dụng khách tức thì của Oracle được cài đặt và thiết lập đúng cách (xem ví dụ: cx_Oracle tài liệu dành cho Ubuntu ).

Sửa khung dữ liệu sau thực tế:

Nếu vì lý do nào đó, bạn không thể sử dụng các lựa chọn thay thế kết nối ở trên, bạn cũng có thể chuyển đổi khung dữ liệu của mình.

  1. Phương án 3:tham gia các mục nhập tuple:

    Bạn có thể sử dụng ''.join() để chuyển đổi bộ giá trị thành chuỗi . Bạn cần thực hiện việc này đối với các mục nhập và tên cột.

    # for all entries that are not None, join the tuples
    for col in df.select_dtypes(include=['object']).columns:
        df[col] = df[col].apply(lambda x: ''.join(x) if x is not None else x)
    
    # also rename the column headings in the same way
    df.rename(columns=lambda x: ''.join(x) if x is not None else x, inplace=True)
    
  2. Phương án 4:thay đổi loại cột:

    Bằng cách thay đổi dtype của một cột bị ảnh hưởng từ object thành string , tất cả các mục nhập cũng sẽ được chuyển đổi. Lưu ý rằng điều này có thể có các tác dụng phụ không mong muốn, như v.d. thay đổi None giá trị cho chuỗi <N/A> . Ngoài ra, bạn sẽ phải đổi tên riêng các tiêu đề cột, như ở trên.

    for col in df.select_dtypes(include=['object']).columns:
        df[col] = df[col].astype('string')
    
    # again, rename headings
    df.rename(columns=lambda x: ''.join(x) if x is not None else x, inplace=True)
    

Tất cả những thứ này ít nhiều phải mang lại cùng một df cuối cùng (ngoài dtypes và có thể thay thế None giá trị):

+---+---------+---------+---------+
|   | COLUMN1 | COLUMN2 | COLUMN3 |
+---+---------+---------+---------+
| 1 | test    | test2   | 1       |
+---+---------+---------+---------+
| 2 | foo     | bar     | 100     |
+---+---------+---------+---------+



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Thiếu tạo tác com.oracle:ojdbc6:jar:11.2.0.3

  2. Nhận các khoảng thời gian chồng chéo của phong bì. I.e

  3. SQL Datatype để sử dụng khi nạp tiền

  4. SQL để trả về số ngày làm việc giữa 2 ngày đã qua

  5. Oracle:tình huống sử dụng RAISE_APPLICATION_ERROR là gì?