2013-08-02 19 views
7

Tôi đang tạo mô-đun Python ở Fortran bằng cách sử dụng f2py. Tôi muốn tạo ra một lỗi (bao gồm cả thông báo lỗi) trong chương trình Python nếu một lỗi gặp phải trong mô-đun Fortran. Hãy xem xét ví dụ sau:Ngừng mã python trong (Fortran) lỗi mô-đun bằng cách sử dụng f2py?

mã Fortran (test.f):

subroutine foo(a,m) 

    integer :: m,i 
    integer, dimension(m) :: a 
    !f2py intent(in) :: m 
    !f2py intent(in,out) :: a 
    !f2py intent(hide), depend(a) :: m=shape(a) 

    do i = 1,m 
    if (a(i) .eq. 0) then 
     print*, 'ERROR HERE..?' 
    end if 
    a(i) = a(i)+1 
    end do 

end subroutine 

chương trình rất đơn giản này cho biết thêm 1 để mỗi phần tử của a. Nhưng sẽ tạo ra lỗi nếu a(i) bằng không. Mã Python đi kèm:

import test 

print test.foo(np.array([1,2],dtype='uint32')) 
print test.foo(np.array([0,2],dtype='uint32')) 

Kết quả bây giờ là:

[2 3] 
ERROR HERE..? 
[1 3] 

Nhưng Tôi muốn chương trình Python để giữ trên lỗi. Hãy giúp tôi.

trả lời

Lệnh stop trong Fortran không chính xác này. Xem xét các mã Fortran Cập nhật:

subroutine foo(a,m) 

    integer :: m,i 
    integer, dimension(m) :: a 
    !f2py intent(in) :: m 
    !f2py intent(in,out) :: a 
    !f2py intent(hide), depend(a) :: m=shape(a) 

    do i = 1,m 
    if (a(i) .eq. 0) then 
     print*, 'Error from Fortran' 
     stop 
    end if 
    a(i) = a(i)+1 
    end do 

end subroutine 

Kết quả bây giờ là:

[2 3] 
Error from Fortran 

Tức là mã Python không tiếp tục sau khi lỗi.

+1

Bạn đang cố gắng tăng ngoại lệ Python từ mô-đun Fortran? – user2357112

+1

Có điều này là chính xác những gì tôi đang cố gắng để làm –

+3

Một cách sẽ là để retutn một mã lỗi từ Fortran, kiểm tra xem nó ở phía python, và nâng cao một ngoại lệ nếu lỗi xảy ra. –

Trả lời

1

f2py cung cấp một số câu lệnh có thể được sử dụng để tăng ngoại lệ. Xem chi tiết tại đây:

http://cens.ioc.ee/projects/f2py2e/usersguide/#statements

Đặc biệt, nhìn vào callstatement trong đó mô tả làm thế nào để thêm f2py_success = 0 mà sẽ kích hoạt một ngoại lệ.

Tôi không chắc chắn điều này sẽ giúp bạn gỡ lỗi nội bộ của thư viện fortran, nhưng ít nhất nó là một sự khởi đầu.

1

Tôi đã đề xuất cộng đồng numpy để thêm một bổ sung f2py "tăng cường" (raise_python_exception), giúp xác định biến chuỗi trong Fortran nếu không trống sẽ khiến Python tăng ngoại lệ khi hàm trả về.

Vì vậy, trong Fortran bạn sẽ viết một cái gì đó như:

subroutine calc_dq(q, temp, dq, error_mesg) 
    !f2py raise_python_exception error_mesg 

    real, intent(in) :: q, temp 
    real, intent(out) :: dq 

    character(len=100), intent(out) :: error_mesg 

    if (.not. init_called()) then 
    error_mesg = "`init` hasn't been called." 
    else 
    call q_flux_function(q, temp, dq) 
    endif 
end subroutine calc_dq 

Và gọi từ Python nội dung của biến error_mesg được sử dụng như nội dung của các ngoại lệ:

In [2]: calc_dq(1.0, 300.) 
--------------------------------------------------------------------------- 
Exception         Traceback (most recent call last) 
<ipython-input-8-c0ce0cb9cda1> in <module>() 
----> 1 calc_dq(1.0, 300.) 

Exception: `init` hasn't been called. 

Tôi nghĩ rằng đây là một cách khá thuận tiện để nâng cao ngoại lệ từ Fortran vì nó cho phép thông báo ngoại lệ được dễ dàng xác định. Tôi đã đặt số suggestion on github của mình.

+0

Giá trị của 'error_mesg' không được xác định trong ví dụ của bạn trong nhánh có điều kiện khác. –

Các vấn đề liên quan