File size: 4,728 Bytes
5543e04
 
95151f6
 
5543e04
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
95151f6
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
db31576
 
95151f6
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
import sympy
from typing import List, Tuple, Union
import gradio as gr
import json

def multiple_integral(expression_str: str, integration_vars: List[Tuple[str, Union[str, float], Union[str, float]]]) -> str:
    """
    Computes definite multiple integrals.

    Args:
        expression_str: The mathematical expression (e.g., "x*y**2").
        integration_vars: A list of tuples, where each tuple contains:
                          (variable_name_str, lower_bound_str_or_float, upper_bound_str_or_float).
                          Example: [("x", "0", "1"), ("y", "0", "x")] for integral from 0 to 1 dx of integral from 0 to x dy of (x*y**2).
                          The order in the list is the order of integration (inner to outer).

    Returns:
        String representation of the integral result or an error message.
    """
    try:
        present_symbols = {sym.name: sym for sym in sympy.parse_expr(expression_str, transformations='all').free_symbols}
        integration_params_sympy = []
        for var_name, lower_bound, upper_bound in integration_vars:
            var_sym = present_symbols.get(var_name, sympy.Symbol(var_name))
            if var_sym.name not in present_symbols:
                present_symbols[var_sym.name] = var_sym
            lower_s = sympy.sympify(lower_bound, locals=present_symbols)
            upper_s = sympy.sympify(upper_bound, locals=present_symbols)
            integration_params_sympy.append((var_sym, lower_s, upper_s))
        if not integration_params_sympy:
            return "Error: No integration variables specified."
        expr = sympy.parse_expr(expression_str, local_dict=present_symbols, transformations='all')
        integral_val = sympy.integrate(expr, *integration_params_sympy)
        return str(integral_val)
    except (sympy.SympifyError, TypeError, SyntaxError) as e:
        return f"Error parsing expression, bounds, or variables: {e}. Ensure bounds are numbers or valid expressions."
    except Exception as e:
        return f"An unexpected error occurred during integration: {e}"

def parse_integration_variables(vars_json_str: str):
    """
    Parses a JSON string representing a list of integration variables and their bounds.
    Expected format: '[["var1", "lower1", "upper1"], ["var2", "lower2", "upper2"]]
    """
    try:
        parsed_list = json.loads(vars_json_str)
        if not isinstance(parsed_list, list):
            raise ValueError("Input must be a JSON list.")
        integration_vars = []
        for item in parsed_list:
            if not (isinstance(item, list) and len(item) == 3):
                raise ValueError("Each item in the list must be a sub-list of three elements: [variable_name, lower_bound, upper_bound].")
            var, low, upp = item
            if not isinstance(var, str):
                raise ValueError(f"Variable name '{var}' must be a string.")
            if not (isinstance(low, (str, int, float))) or not (isinstance(upp, (str, int, float))):
                raise ValueError(f"Bounds for variable '{var}' must be numbers or strings. Got '{low}' and '{upp}'.")
            integration_vars.append((str(var), str(low), str(upp)))
        return integration_vars
    except json.JSONDecodeError:
        raise gr.Error("Invalid JSON format for integration variables.")
    except ValueError as ve:
        raise gr.Error(str(ve))
    except Exception as e:
        raise gr.Error(f"Unexpected error parsing integration variables: {str(e)}")

multiple_integral_interface = gr.Interface(
    fn=lambda expr_str, vars_json_str: multiple_integral(expr_str, parse_integration_variables(vars_json_str)),
    inputs=[
        gr.Textbox(label="Expression (e.g., x*y**2, 1)", value="x*y"),
        gr.Textbox(
            label="Integration Variables and Bounds (JSON list of [var, low, upp] tuples, inner to outer)",
            value='[["y", "0", "x"], ["x", "0", "1"]]',
            info="Example: integral_0^1 dx integral_0^x dy (x*y) is [['y', '0', 'x'], ['x', '0', '1']]"
        )
    ],
    outputs="text",
    title="Definite Multiple Integral Calculator",
    description="Compute multiple integrals.\n\n**Description:**\nThis tool computes definite multiple integrals for a given expression and bounds. The order of variables in the list is inner-most integral first.\n\n**Examples:**\n- Expression: x*y, Variables: [[\"y\", \"0\", \"x\"], [\"x\", \"0\", \"1\"]] → Output: 1/6\n- Expression: x**2, Variables: [[\"x\", \"0\", \"2\"]] → Output: 8/3\n- Expression: 1, Variables: [[\"x\", \"0\", \"1\"], [\"y\", \"0\", \"1\"]] → Output: 1",
    examples=[["x*y", '[["y", "0", "x"], ["x", "0", "1"]]'], ["x**2", '[["x", "0", "2"]]'], ["1", '[["x", "0", "1"], ["y", "0", "1"]]']],
)