Рубрики
Без рубрики

Создайте свой следующий проект с Wolfram Api и Python

Любой, кто в какой -то момент боролся с математикой, знает Wolfram Alpha и, вероятно, был спасен его абили … Tagged with Python, Tutorial, API, WebDev.

Любой, кто в какой -то момент боролся с математикой, знает Wolfram Alpha и, вероятно, был сохранен благодаря ее способности решать любые уравнения, построить любую функцию или визуализировать логические схемы. Wolfram Alpha Can; Тем не менее, сделайте гораздо больше, включая химию, лингвистику или историю и, что самое важное – это может дать вам все ответы, используя свой публичный API. Итак, в этой статье мы рассмотрим, как вы можете использовать его, чтобы ответить на простые вопросы, решить математические задачи, рендеринг или даже описать последовательности ДНК!

Настройка

Wolfram API API бесплатен (для некоммерческого использования), но нам все еще нужно получить ключ API (APPID) для выполнения запросов против конечных точек API. Чтобы получить ключ API, мы сначала создадим ID Wolfram в https://account.wolfram.com/login/create . Когда создается учетная запись, мы можем перейти к https://developer.wolframalpha.com/portal/myapps/index.html , нажмите на Зарегистрируйтесь, чтобы получить свой первый Appid кнопка, заполнить Получите новую Appid диалог После этого нам будет представлена API -ключ, который называется Appid Здесь, которое мы можем проверить с помощью следующего образца запроса:

from pprint import pprint
import requests
import os
import urllib.parse

appid = os.getenv('WA_APPID', '...')

query = urllib.parse.quote_plus("lifespan of a mosquito")
query_url = f"http://api.wolframalpha.com/v2/query?" \
             f"appid={appid}" \
             f"&input={query}" \
             f"&format=plaintext" \
             f"&output=json"

r = requests.get(query_url).json()

data = r["queryresult"]["pods"][0]["subpods"][0]
datasource = ", ".join(data["datasources"]["datasource"])
microsource = data["microsources"]["microsource"]
plaintext = data["plaintext"]

print(f"Result: '{plaintext}' from {datasource} ({microsource}).")
# Result: '(9.2 to 11, 52 to 60) days' from AmazingNumbers, TheWikimediaFoundationIncWikipedia (SpeciesData).

Приведенный выше код использует Вольфрам | Альфа Полные результаты API Чтобы узнать, что такое срок службы комаров. Для этого это делает Получить запрос на http://api.wolframalpha.com/v2/query С параметрами, указывающими нашу приложение для аутентификации, вопрос в Вход поле, параметр формата как открытый текст (вместо изображения) и, наконец, вывод типа, который является JSON (вместо по умолчанию XML).

Мы пересекаем результат как словарь, ищем интересные поля для распечатки. Возвращенный JSON (или XML) может быть довольно сложным, и действительно самым простым способом проанализировать его, это распечатать его и найти любые полезные поля там. Обрезанный пример ответа для вышеупомянутого запроса будет выглядеть примерно так:

{'queryresult': {'error': False,
                 'pods': [{'error': False,
                           'expressiontypes': {'name': 'Default'},
                           'id': 'Result',
                           'numsubpods': 1,
                           'position': 100,
                           'primary': True,
                           'scanner': 'Data',
                           'subpods': [{'datasources': {'datasource': ['AmazingNumbers',
                                                                       'TheWikimediaFoundationIncWikipedia']},
                                        'microsources': {'microsource': 'SpeciesData'},
                                        'plaintext': '(9.2 to 11, 52 to 60) '
                                                     'days',
                                        'title': ''}],
                           'title': 'Result'}],
                 'success': True}}

Делая математику

Наиболее полезной частью Wolfram Alpha (на мой взгляд) является способность решать сложные математические задачи. Итак, давайте попробуем использовать API, чтобы сделать математику:

equation = "7 + 2x = 12 - 3x"
query = urllib.parse.quote_plus(f"solve {equation}")
query_url = f"http://api.wolframalpha.com/v2/query?" \
            f"appid={appid}" \
            f"&input={query}" \
            f"&includepodid=Result" \
            f"&output=json"

r = requests.get(query_url).json()

data = r["queryresult"]["pods"][0]["subpods"][0]
plaintext = data["plaintext"]

print(f"Result of {equation} is '{plaintext}'.")
# Result of 7 + 2x = 12 - 3x is 'x = 1'.

Полные результаты API Показанный в предыдущем разделе не просто отвечает на некоторые любопытные вопросы, но и делает математику (и на самом деле почти все). Чтобы API осознал, что мы хотим сделать математику – в данном случае – решить уравнение, нам нужно подготовить фактическое уравнение с помощью слова решать . Помимо самого ввода, запрос выглядит очень похоже на тот, который в предыдущем разделе. Одна дополнительная вещь, которая добавлена к этому, это IncludePodid Параметр, который сообщает API, что в этом случае мы хотим только Результат стручок, чтобы быть включенным в ответ. “Что такое POD, хотя?” Вы можете спросить.

Каждый результат Wolfram Alpha (как веб -сайт, так и API), как правило, включает в себя несколько категорий данных. Это может быть, например, график, изображение, пошаговое решение или таблица. Каждый из них принадлежит своему собственному разделу под названием POD , который, в свою очередь, включает подподы которые содержат отдельные части данных. Учитывая, что каждый ответ иногда может включать в себя даже 10 стручков, желательно описать то, что мы хотим получить от API. Для этого – Podtitle и более надежный IncludePodid – Параметры могут быть использованы, как показано выше.

Поэтому отфильтрованный ответ для вышеупомянутого запроса будет выглядеть так:

{'queryresult': {'pods': [{'error': False,
                           'expressiontypes': {'name': 'Default'},
                           'id': 'Result',
                           'numsubpods': 1,
                           'position': 100,
                           'primary': True,
                           'scanner': 'Solve',
                           'states': [{'input': 'Result__Step-by-step solution',
                                       'name': 'Step-by-step solution',
                                       'stepbystep': True}],
                           'subpods': [{'img': {'alt': 'x = 1',
                                                'src': 'https://www5a.wolframalpha.com/Calculate/MSP/MSP31791g2156fih7b062ii00002a9h8g45379f9127?MSPStoreType=image/gif&s=50',
                                                'themes': '1,2,3,4,5,6,7,8,9,10,11,12',
                                                'title': 'x = 1'},
                                        'plaintext': 'x = 1',
                                        'title': ''}],
                           'title': 'Result'}]}}

И для сравнения того же (но графического) результата, но со всеми стручками выглядели так:

Wolfram Alpha может быть отличным учебным ресурсом благодаря возможности показать не только результаты, но и все шаги вычислений и API тоже могут это сделать. Чтобы получить пошаговое решение для запроса, нам нужно включить еще один параметр под названием Podstate , что указывает изменение состояния POD. Это заменит исходный POD на модифицированную версию, которая может быть – например, – больше цифр для десятичного числа, таких как PI ( decimalApproximation ), расширенные данные о погоде (больше дней/месяцев/лет) или, как в нашем случае – шаги для уравнения решение:

equation = "7 + 2x = 12 - 3x"
query = urllib.parse.quote_plus(f"solve {equation}")
query_url = f"http://api.wolframalpha.com/v2/query?" \
            f"appid={appid}" \
            f"&input={query}" \
            f"&scanner=Solve" \
            f"&podstate=Result__Step-by-step+solution" \
            "&format=plaintext" \
            f"&output=json"

r = requests.get(query_url).json()

data = r["queryresult"]["pods"][0]["subpods"]
result = data[0]["plaintext"]
steps = data[1]["plaintext"]

print(f"Result of {equation} is '{result}'.\n")
print(f"Possible steps to solution:\n\n{steps}")

# Result of 7 + 2x = 12 - 3x is 'x = 1'.
#
# Possible steps to solution:
#
# Solve for x:
# 2 x + 7 = 12 - 3 x
# Add 3 x to both sides:
# 3 x + 2 x + 7 = (3 x - 3 x) + 12
# 3 x - 3 x = 0:
# 3 x + 2 x + 7 = 12
# Grouping like terms, 3 x + 2 x + 7 = (2 x + 3 x) + 7:
# (2 x + 3 x) + 7 = 12
# 2 x + 3 x = 5 x:
# 5 x + 7 = 12
# Subtract 7 from both sides:
# 5 x + (7 - 7) = 12 - 7
# 7 - 7 = 0:
# 5 x = 12 - 7
# 12 - 7 = 5:
# 5 x = 5
# Divide both sides of 5 x = 5 by 5:
# (5 x)/5 = 5/5
# 5/5 = 1:
# x = 5/5
# 5/5 = 1:
# Answer: x = 1

Предоставление математической отметки

Один из аккуратных трюков, для которого вы можете использовать API Wolfram API, – это рендеринг MathML. Если вы не знакомы с Mathml, то вот быстрое изложение – Mathml означает Математический язык разметки , это формат на основе XML для рендеринга Латекс Подобно математическим выражениям в веб -браузерах. Несмотря на то, что этот формат существует в течение долгого времени, он действительно поддерживается только Firefox, что может сделать его как плохой выбор, но двигатель дисплея JavaScript под названием Mathjax.js делает возможным отображать MathML в любом браузере, что делает его хорошим выбором, если вы хотите показать действительно красивые сложные формулы в Латекс формат в вашем веб -приложении или в блоге. С учетом сказанного, давайте запрашиваем это!

equation = "7 + 2x = 12 - 3x"
query = urllib.parse.quote_plus(f"solve {equation}")
query_url = f"http://api.wolframalpha.com/v2/query?" \
            f"appid={appid}" \
            f"&input={query}" \
            f"&scanner=Solve" \
            f"&podstate=Result__Step-by-step+solution" \
            "&format=mathml" \
            f"&output=json"

r = requests.get(query_url).json()

data = r["queryresult"]["pods"][0]["subpods"]
result = data[0]["mathml"]
steps = data[1]["mathml"]

print(f"MathML result of {equation} is:\n")
print(f"{result}")
print(f"Possible steps to solution:\n\n{steps}")

# MathML result of 7 + 2x = 12 - 3x is:
#
# 
#  
#   x
#   =
#   1
#  
# 
#
# Possible steps to solution:
# 
#  
#   
#     ...
#   
#  
# 

Мы снова используем пример из предыдущего раздела для уравнения запроса с помощью пошагового решения, но заменить Format = plaintext для format = mathml и аналогично замену всех других случаев открытый текст с Mathml Например, Результат [0] ["mathml"] Анкет Выше вы можете увидеть немного вывода MathML, который был дан API, он очень обрезан, так как полный выходной Латекс Математические выражения.

Решение логической алгебры

Еще один довольно распространенный вариант использования для Wolfram Alpha – решать логическую алгебру. То же самое, что и с основными уравнениями, все, что нам нужно сделать, это передать формулу API, и это то, что мы вернем:

formula = "((P AND (Q IMPLIES R)) OR S) AND T"
query = urllib.parse.quote_plus(f"solve {formula}")
query_url = f"http://api.wolframalpha.com/v2/query?" \
            f"appid={appid}" \
            f"&input=solve {formula}" \
            f"&output=json" \
            f"&includepodid=Input" \
            f"&includepodid=MinimalForms" \
            f"&includepodid=TruthDensity"

r = requests.get(query_url).json()

pods = r["queryresult"]["pods"]
expression = pods[0]["subpods"][0]["plaintext"]
min_forms = "\n".join(pods[1]["subpods"][0]["plaintext"].split("\n")[:-1])
truth_density = pods[2]["subpods"][0]["plaintext"].split()

print(f"Expression {expression}: \n")
print(f"{min_forms}\n")
print(f"Truth density equals {truth_density[0]} which is {truth_density[1]}")

# Expression ((P ∧ (Q implies R)) ∨ S) ∧ T:
#
# DNF  | (P ∧ ¬Q ∧ T) ∨ (P ∧ R ∧ T) ∨ (S ∧ T)
# CNF  | (P ∨ S) ∧ (¬Q ∨ R ∨ S) ∧ T
# ANF  | (P ∧ T) ⊻ (S ∧ T) ⊻ (P ∧ Q ∧ T) ⊻ (P ∧ S ∧ T) ⊻ (P ∧ Q ∧ R ∧ T) ⊻ (P ∧ Q ∧ S ∧ T) ⊻ (P ∧ Q ∧ R ∧ S ∧ T)
# NOR  | (P ⊽ S) ⊽ (¬Q ⊽ R ⊽ S) ⊽ ¬T
# NAND | (P ⊼ ¬Q ⊼ T) ⊼ (P ⊼ R ⊼ T) ⊼ (S ⊼ T)
# AND  | ¬(¬P ∧ ¬S) ∧ ¬(Q ∧ ¬R ∧ ¬S) ∧ T
# OR   | ¬(¬P ∨ Q ∨ ¬T) ∨ ¬(¬P ∨ ¬R ∨ ¬T) ∨ ¬(¬S ∨ ¬T)
#
# Truth density equals 11/32 which is 34.375%

Запрос выше на самом деле не показывает ничего нового, за исключением конкретных стручков, которые мы выбрали – Вход В Минималиформы и Правда, Анкет После анализа данных в этих 3 стручках мы можем увидеть вывод, который включает в себя более хорошую форму представленной входной формулы, это другие вычисленные формы (CNF, DNF …), а также плотность истины как в виде фракции, так и в процентах.

Рендеринг и загрузка графиков

Одна из моих любимых вещей, связанных с Wolfram Alpha, всегда делала сложные сюжеты. Реализация этого даже не требует большого изменения кода, единственным реальным изменением является выбор стручков и их полей:

function = "sin x cos y"
query = f"plot {function}"
query_url = f"http://api.wolframalpha.com/v2/query?" \
            f"appid={appid}" \
            f"&input={query}" \
            f"&output=json" \
            f"&includepodid=3DPlot" \
            f"&includepodid=ContourPlot"

r = requests.get(query_url).json()

pods = r["queryresult"]["pods"]
plot_3d_url = pods[0]["subpods"][0]["img"]["src"]
plot_contour_url = pods[1]["subpods"][0]["img"]["src"]

img_name = "3d_plot.jpg"
img_data = requests.get(plot_3d_url).content
with open(img_name, 'wb') as handler:
    handler.write(img_data)
    print(f"3D Plot Image Saved to {img_name}.")

В этом случае мы используем IncludePodid Параметр для выбора 3dplot и Contourplot стручки, которые удерживают URL -адреса на изображениях соответствующих участков в их img.src поля. Эти графики могут быть загружены и написаны в бинарном режиме, создавая следующее изображение:

Не только математика

На данный момент, я думаю, мы видели достаточно приложений для Wolfram Alpha и Math. Итак, что еще мы можем сделать? В качестве простого примера давайте рассмотрим некоторую последовательность ДНК:

query = "AAGCTAGCTAGC"
query_url = f"http://api.wolframalpha.com/v2/query?" \
            f"appid={appid}" \
            f"&input={query}" \
            f"&scanner=Genome" \
            f"&output=json" \
            f"&includepodid=Length" \
            f"&includepodid=AminoAcidSequence" \
            f"&includepodid=MeltingTemperature" \

r = requests.get(query_url).json()

pods = r["queryresult"]["pods"]

length = {
    "title": pods[0]["title"],
    "value": pods[0]["subpods"][0]["plaintext"]
}
amino_sequence = {
    "title": pods[1]["title"],
    "value": pods[1]["subpods"][0]["plaintext"].replace(") ", ")\n")
}
melting_temp = {
    "title": pods[2]["title"],
    "value": pods[2]["subpods"][0]["plaintext"]
}

print(f"{length['title']}: {length['value']}\n")
print(f"{amino_sequence['title']}:\n {amino_sequence['value']}\n")
print(f"{melting_temp['title']}: {melting_temp['value']}")

# Length: 12 base pairs
#
# Amino acid sequence:
#  (5'-3' frame 1)
# | AAG | CUA | GCU | AGC
#    ↓  |  ↓  |  ↓  |  ↓
#   Lys | Leu | Ala | Ser
#
# Oligonucleotide melting temperature: 48.5 °C (degrees Celsius)
# (under standard PCR conditions)

Мы снова используем одну и ту же конечную точку API, но на этот раз мы отправляем строку, представляющую последовательность ДНК. Вы можете заметить, что нам не нужно было включать ключевое слово, прежде чем запрос, как ранее, с Решите или Сюжет Анкет Ну, на этот раз вместо использования ключевого слова мы добавили сканер Параметр, который указывает область предмета поискового запроса, которая в этом случае является Геном Анкет Чтобы найти, какой сканер вернет соответствующие данные для некоторого запроса, легко запустить запрос без сканер параметр и ищите сканер Атрибут каждого стручка, который имеет ожидаемые данные.

Последовательности ДНК, очевидно, не единственная крутая вещь, которую вы можете искать. Некоторые из других интересных тем могут быть, например, история, химия, транспорт или музыка – лишь некоторые из них.

Натуральный язык (разговорный) Ответы

Если вы только ищете информацию, то достаточно примеров и API в предыдущих примерах. Однако, если вы хотите/нуждаетесь в более естественном ответе на свои запросы, то вы можете использовать Разговорные результаты API :

question = "what is the most spoken language in the world?"
query_url = f"http://api.wolframalpha.com/v1/spoken?" \
            f"appid={appid}" \
            f"&i={question}" \

r = requests.get(query_url)

print(r.text)
# The most spoken language by total number of speakers is English. The total number of English speakers is about 1.3 billion people

Запросы для v1/Contkude Конечная точка очень проста. Все, что нам нужно пройти, это аппетита и наши вопросы в я параметр. Это дает ответ в форме полного предложения, а не простого факта. Это может быть весьма полезно при создании умных чат-ботов или, возможно, в качестве входного сигнала для двигателя текста в речь.

Общение с API разговора

Как своего рода расширение на Разговорные результаты API , Wolfram Alpha также предоставляет Разговорной API , что позволяет вам задавать последующие вопросы и, следовательно, поговорить с API. Итак, давайте попробуем и спросим что -нибудь Wolfram Alpha:

question = "Where are Falkland Islands?"
location = "47.01,16.93"
query_url = f"http://api.wolframalpha.com/v1/conversation.jsp?" \
            f"appid={appid}" \
            f"&geolocation={appid}" \
            f"&i={question}" \

r = requests.get(query_url).json()
answer = r["result"]
conversation_id = r["conversationID"]
host = r["host"]

print(f"{question}: '{answer}'")

followup_question = "How far is it from here?"
query_url = f"http://{host}/api/v1/conversation.jsp?" \
            f"appid={appid}" \
            f"&conversationID={conversation_id}" \
            f"&i={followup_question}" \

r = requests.get(query_url).json()
answer = r["result"]
print(f"{followup_question}: '{answer}'")


# Where are Falkland Islands?: 'The Falkland Islands is in South America.'
# How far is it from here?: 'The answer is about 13217 kilometers.'

Учитывая, что мы хотим задать несколько вопросов, мы также должны задавать несколько запросов. Первый из них направлен на v1/разговор конечная точка и включает вопросы в я параметр. Мы также указываем наше местоположение с Геолокация Параметр – это одно из необязательных значений (другие – это ip и единицы ) Это может предоставить контекст для вопросов. Этот первый запрос в значительной степени делает то же самое, что и Разговорные результаты API , это означает, что он возвращает информацию в форме полного предложения.

Веселье начинается, когда мы задаем последующие вопросы. Для этого мы делаем еще один запрос, на этот раз мы отправляем его хозяину, который был предоставлен как часть ответа на первый запрос ( host ["host"] ). Первый ответ также включал разговор который мы также должны передать API, чтобы узнать, что было сказано до этого.

Затем второй запрос возвращает тот же тип результата, что и первый, который позволяет нам продолжать задавать больше вопросов, используя предоставленные разговор и хост Анкет

И последнее, что я хочу выделить здесь, это то, как вопросы и ответы могут хорошо течь и использовать контекст. В этом конкретном примере мы использовали “Насколько это далеко отсюда?” как вопрос, не указав, что “Это” или “Здесь” на самом деле. Эта информация была автоматически выведена из предыдущего вопроса и Геолокация параметр.

Вывод

Эта статья на самом деле является просто верхушкой айсберга, поскольку информация, доступная от Wolfram Alpha. Эти API могут быть использованы для гораздо большего, чем просто математика, и я думаю, что это отличная отправная точка для создания прохладных ботов, интеллектуальных устройств или голосовых приложений. Несмотря на то, что это не бесплатно для коммерческого использования, вы по -прежнему получаете 2000 запросов в месяц, что будет достаточно, чтобы начать классный проект. Я рекомендую проверить https://products.wolframalpha.com/api/ Для документации для каждой конечной точки API, а также Вульфрам альфа -целевая страница что показывает все различные темы, которые могут дать вам представление о том, что вы могли бы построить с ним. 😉

Оригинал: “https://dev.to/martinheinz/build-your-next-project-with-wolfram-alpha-api-and-python-l6l”