A Gentle Intro To Chaining LLMS, Agents, and Utils Via LangChain

You might also like

Download as pdf or txt
Download as pdf or txt
You are on page 1of 26

10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr.

ngChain | by Dr. Varshita Sher | Towards Data Science

Open in app

Search

Get unlimited access to the best of Medium for less than $1/week. Become a member

#LLM FOR BEGINNERS

A Gentle Intro to Chaining LLMs, Agents, and


utils via LangChain
Understand the basics of agents, tools, and prompts and some learnings along the
way

Dr. Varshita Sher · Follow


Published in Towards Data Science
20 min read · Apr 22

Listen Share More

Audience: For those feeling overwhelmed with the giant (yet brilliant) library…

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 1/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Image generated by Author using DALL.E 2

Introduction
I’d be lying if I said I have got the entire LangChain library covered — in fact, I am

🚀
far from it. But the buzz surrounding it was enough to shake me out of my writing
hiatus and give it a go .

The initial motivation was to see what was it that LangChain was adding (on a
practical level) that set it apart from the chatbot I built last month using the
ChatCompletion.create() function from the openai package. Whilst doing so, I
realized I needed to understand the building blocks for LangChain first before
moving on to the more complex parts.

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 2/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

This is what this article does. Heads-up though, there will be more parts coming as I
am truly fascinated by the library and will continue to explore to see what all can be
built through it.

Let’s begin by understanding the fundamental building blocks of LangChain — i.e.


Chains. If you’d like to follow along, here’s the GitHub repo.

What are chains in LangChain?


Chains are what you get by connecting one or more large language models (LLMs)
in a logical way. (Chains can be built of entities other than LLMs but for now, let’s
stick with this definition for simplicity).

OpenAI is a type of LLM (provider) that you can use but there are others like Cohere,
Bloom, Huggingface, etc.

Note: Pretty much most of these LLM providers will need you to request an API key in order
to use them. So make sure you do that before proceeding with the remainder of this blog.
For example:

import os
os.environ["OPENAI_API_KEY"] = "..."

P.S. I am going to use OpenAI for this tutorial because I have a key with credits that expire
in a month’s time, but feel free to replace it with any other LLM. The concepts covered here
will be useful regardless.

Chains can be simple (i.e. Generic) or specialized (i.e. Utility).

1. Generic — A single LLM is the simplest chain. It takes an input prompt and the
name of the LLM and then uses the LLM for text generation (i.e. output for the
prompt). Here’s an example:

Let’s build a basic chain — create a prompt and get a prediction


Prompt creation (using PromptTemplate ) is a bit fancy in Lanchain but this is
probably because there are quite a few different ways prompts can be created
depending on the use case (we will cover AIMessagePromptTemplate ,

HumanMessagePromptTemplate etc. in the next blog post). Here’s a simple one for now:

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 3/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

from langchain.prompts import PromptTemplate

prompt = PromptTemplate(
input_variables=["product"],
template="What is a good name for a company that makes {product}?",
)

print(prompt.format(product="podcast player"))

# OUTPUT
# What is a good name for a company that makes podcast player?

Note: If you require multiple input_variables , for instance: input_variables=["product",

"audience"] for a template such as “What is a good name for a company that makes

{product} for {audience}” , you need to do print(prompt.format(product="podcast

player", audience="children”) to get the updated prompt.

Once you have built a prompt, we can call the desired LLM with it. To do so, we
create an LLMChain instance (in our case, we use OpenAI 's large language model
text-davinci-003 ). To get the prediction (i.e. AI-generated text), we use run function
with the name of the product .

from langchain.llms import OpenAI


from langchain.chains import LLMChain

llm = OpenAI(
model_name="text-davinci-003", # default model
temperature=0.9) #temperature dictates how whacky the output should b
llmchain = LLMChain(llm=llm, prompt=prompt)
llmchain.run("podcast player")

# OUTPUT
# PodConneXion

If you had more than one input_variables, then you won’t be able to use run .

Instead, you’ll have to pass all the variables as a dict . For example,
llmchain({“product”: “podcast player”, “audience”: “children”}) .

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 4/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Note 1: According to OpenAI, davinci text-generation models are 10x more expensive
than their chat counterparts i.e gpt-3.5-turbo , so I tried to switch from a text model to a
chat model (i.e. from OpenAI to ChatOpenAI ) and the results are pretty much the same.

Note 2: You might see some tutorials using OpenAIChat instead of ChatOpenAI . The former
is deprecated and will no longer be supported and we are supposed to use ChatOpenAI .

from langchain.chat_models import ChatOpenAI

chatopenai = ChatOpenAI(
model_name="gpt-3.5-turbo")
llmchain_chat = LLMChain(llm=chatopenai, prompt=prompt)
llmchain_chat.run("podcast player")

# OUTPUT
# PodcastStream

This concludes our section on simple chains. It is important to note that we rarely
use generic chains as standalone chains. More often they are used as building
blocks for Utility chains (as we will see next).

2. Utility — These are specialized chains, comprised of many LLMs to help solve a
specific task. For example, LangChain supports some end-to-end chains (such as
AnalyzeDocumentChain for summarization, QnA, etc) and some specific ones (such as
GraphQnAChain for creating, querying, and saving graphs). We will look at one
specific chain called PalChain in this tutorial for digging deeper.

PAL stands for Programme Aided Language Model. PALChain reads complex math
problems (described in natural language) and generates programs (for solving the
math problem) as the intermediate reasoning steps, but offloads the solution step to
a runtime such as a Python interpreter.

To confirm this is in fact true, we can inspect the _call() in the base code here.
Under the hood, we can see this chain:

first uses a generic LLMChain to understand the query we pass to it and get a
prediction. Thus, this chain requires passing an LLM at the time of initializing
(we are going to use the same OpenAI LLM as before).

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 5/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

second, it uses Python REPL to solve the function/program outputted by the


LLM.

P.S. It is a good practice to inspect _call() in base.py for any of the chains in LangChain
to see how things are working under the hood.

from langchain.chains import PALChain


palchain = PALChain.from_math_prompt(llm=llm, verbose=True)
palchain.run("If my age is half of my dad's age and he is going to be 60 next y

# OUTPUT
# > Entering new PALChain chain...
# def solution():
# """If my age is half of my dad's age and he is going to be 60 next year, w
# dad_age_next_year = 60
# dad_age_now = dad_age_next_year - 1
# my_age_now = dad_age_now / 2
# result = my_age_now
# return result
#
# > Finished chain.
# '29.5'

Note1: verbose can be set to False if you do not need to see the intermediate step.

Now some of you may be wondering — but what about the prompt? We certainly didn’t
pass one as we did for the generic llmchain we built. The fact is, it is automatically
loaded when using .from_math_prompt() . You can check the default prompt using
palchain.prompt.template or you can directly inspect the prompt file here.

print(palchain.prompt.template)
# OUTPUT
# 'Q: Olivia has $23. She bought five bagels for $3 each. How much money does s

Note: Most of the utility chains will have their prompts pre-defined as part of the library
(check them out here). They are, at times, quite detailed (read: lots of tokens) so there is

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 6/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

definitely a trade-off between cost and the quality of response from the LLM.

Are there any Chains that don’t need LLMs and prompts?
Even though PalChain requires an LLM (and a corresponding prompt) to parse the user’s
question written in natural language, there are some chains in LangChain that don’t need
one. These are mainly transformation chains that preprocess the prompt, such as removing
extra spaces, before inputting it into the LLM. You can see another example here.
Can we get to the good part and start creating chains?
Of course, we can! We have all the basic building blocks we need to start chaining
together LLMs logically such that input from one can be fed to the next. To do so, we
will use SimpleSequentialChain .

The documentation has some great examples on this, for example, you can see here
how to have two chains combined where chain#1 is used to clean the prompt
(remove extra whitespaces, shorten prompt, etc) and chain#2 is used to call an LLM
with this clean prompt. Here’s another one where chain#1 is used to generate a
synopsis for a play and chain#2 is used to write a review based on this synopsis.

While these are excellent examples, I want to focus on something else. If you
remember before, I mentioned that chains can be composed of entities other than
LLMs. More specifically, I am interested in chaining agents and LLMs together. But
first, what are agents?
Using agents for dynamically calling LLMs
It will be much easier to explain what an agent does vs. what it is.

Say, we want to know the weather forecast for tomorrow. If were to use the simple
ChatGPT API and give it a prompt Show me the weather for tomorrow in London , it
won’t know the answer because it does not have access to real-time data.

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 7/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Wouldn’t it be useful if we had an arrangement where we could utilize an LLM for


understanding our query (i.e prompt) in natural language and then call the weather
API on our behalf to fetch the data needed? This is exactly what an agent does
(amongst other things, of course).

An agent has access to an LLM and a suite of tools for example Google Search, Python
REPL, math calculator, weather APIs, etc.

There are quite a few agents that LangChain supports — see here for the complete
list, but quite frankly the most common one I came across in tutorials and YT videos
was zero-shot-react-description . This agent uses ReAct (Reason + Act) framework
to pick the most usable tool (from a list of tools), based on what the input query is.

P.S.: Here’s a nice article that goes in-depth into the ReAct framework.

Let’s initialize an agent using initialize_agent and pass it the tools and LLM it
needs. There’s a long list of tools available here that an agent can use to interact with
the outside world. For our example, we are using the same math-solving tool as
above, called pal-math . This one requires an LLM at the time of initialization, so we
pass to it the same OpenAI LLM instance as before.

from langchain.agents import initialize_agent


from langchain.agents import AgentType
from langchain.agents import load_tools

llm = OpenAI(temperature=0)
tools = load_tools(["pal-math"], llm=llm)

agent = initialize_agent(tools,
llm,
agent=AgentType.ZERO_SHOT_REACT_DESCRIPTION,
verbose=True)

Let’s test it out on the same example as above:

agent.run("If my age is half of my dad's age and he is going to be 60 next year

# OUTPUT
# > Entering new AgentExecutor chain...

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 8/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

# I need to figure out my dad's current age and then divide it by two.
# Action: PAL-MATH
# Action Input: What is my dad's current age if he is going to be 60 next year?
# Observation: 59
# Thought: I now know my dad's current age, so I can divide it by two to get my
# Action: Divide 59 by 2
# Action Input: 59/2
# Observation: Divide 59 by 2 is not a valid tool, try another one.
# Thought: I can use PAL-MATH to divide 59 by 2.
# Action: PAL-MATH
# Action Input: Divide 59 by 2
# Observation: 29.5
# Thought: I now know the final answer.
# Final Answer: My current age is 29.5 years old.

# > Finished chain.


# 'My current age is 29.5 years old.'

Note 1: At each step, you’ll notice that an agent does one of three things — it either has an
observation , a thought , or it takes an action . This is mainly due to the ReAct
framework and the associated prompt that the agent is using:

print(agent.agent.llm_chain.prompt.template)
# OUTPUT
# Answer the following questions as best you can. You have access to the follow
# PAL-MATH: A language model that is really good at solving complex word math p

# Use the following format:

# Question: the input question you must answer


# Thought: you should always think about what to do
# Action: the action to take, should be one of [PAL-MATH]
# Action Input: the input to the action
# Observation: the result of the action
# ... (this Thought/Action/Action Input/Observation can repeat N times)
# Thought: I now know the final answer
# Final Answer: the final answer to the original input question
# Begin!
# Question: {input}
# Thought:{agent_scratchpad}

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 9/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Note2: You might be wondering what’s the point of getting an agent to do the same thing
that an LLM can do. Some applications will require not just a predetermined chain of calls
to LLMs/other tools, but potentially an unknown chain that depends on the user’s input
[Source]. In these types of chains, there is an “agent” which has access to a suite of tools.
For instance, here’s an example of an agent that can fetch the correct documents (from the
vectorstores) for RetrievalQAChain depending on whether the question refers to document
A or document B.

For fun, I tried making the input question more complex (using Demi Moore’s age as
a placeholder for Dad’s actual age).

agent.run("My age is half of my dad's age. Next year he is going to be same age

Unfortunately, the answer was slightly off as the agent was not using the latest age
for Demi Moore (since Open AI models were trained on data until 2020). This can be
easily fixed by including another tool —
tools = load_tools([“pal-math”, "serpapi"], llm=llm) . serpapi is useful for
answering questions about current events.

Note: It is important to add as many tools as you think may be relevant to the user query.
The problem with using a single tool is that the agent keeps trying to use the same tool even
if it’s not the most relevant for a particular observation/action step.

Here’s another example of a tool you can use — podcast-api . You need to get your
own API key and plug it into the code below.

tools = load_tools(["podcast-api"], llm=llm, listen_api_key="...")


agent = initialize_agent(tools,
llm,
agent=AgentType.ZERO_SHOT_REACT_DESCRIPTION,
verbose=True)

agent.run("Show me episodes for money saving tips.")

# OUTPUT
# > Entering new AgentExecutor chain...

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 10/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

# I should search for podcasts or episodes related to money saving


# Action: Podcast API
# Action Input: Money saving tips
# Observation: The API call returned 3 podcasts related to money saving tips:
# Thought: I now have some options to choose from
# Final Answer: The Money Nerds, The Rachel Cruze Show, and The Martin Lewis Po

# > Finished chain.

# 'The Money Nerds, The Rachel Cruze Show, and The Martin Lewis Podcast are gre

Note1: There is a known error with using this API where you might see,
openai.error.InvalidRequestError: This model’s maximum context length is 4097

tokens, however you requested XXX tokens (XX in your prompt; XX for the

completion). Please reduce your prompt; or completion length. This happens when the
response returned by the API might be too big. To work around this, the documentation
suggests returning fewer search results, for example, by updating the question to "Show me

episodes for money saving tips, return only 1 result" .

Note2: While tinkering around with this tool, I noticed some inconsistencies. The responses
aren’t always complete the first time around, for instance here are the input and responses
from two consecutive runs:

Input: “Podcasts for getting better at French”

Response 1: “The best podcast for learning French is the one with the highest review score.”
Response 2: ‘The best podcast for learning French is “FrenchPod101”.

Under the hood, the tool is first using an LLMChain for building the API URL based
on our input instructions (something along the lines of https://listen-

api.listennotes.com/api/v2/search?q=french&type=podcast&page_size=3 ) and making


the API call. Upon receiving the response, it uses another LLMChain that
summarizes the response to get the answer to our original question. You can check
out the prompts here for both LLMchains which describe the process in more detail.

I am inclined to guess the inconsistent results seen above are resulting from the
summarization step because I have separately debugged and tested the API URL
(created by LLMChain#1) via Postman and received the right response. To further
confirm my doubts, I also stress-tested the summarization chain as a standalone

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 11/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

🤷‍♀
chain with an empty API URL hoping it would throw an error but got the response
“Investing’ podcasts were found, containing 3 results in total.” I’d be curious to see if
others had better luck than me with this tool!

Use Case 2: Combine chains to create an age-appropriate gift generator


Let’s put our knowledge of agents and sequential chaining to good use and create
our own sequential chain. We will combine:

Chain #1 — The agent we just created that can solve age problems in math.

Chain #2 — An LLM that takes the age of a person and suggests an appropriate
gift for them.

# Chain1 - solve math problem, get the age


chain_one = agent

# Chain2 - suggest age-appropriate gift


template = """You are a gift recommender. Given a person's age,\n
it is your job to suggest an appropriate gift for them.

Person Age:
{age}
Suggest gift:"""
prompt_template = PromptTemplate(input_variables=["age"], template=template)
chain_two = LLMChain(llm=llm, prompt=prompt_template)

Now that we have both chains ready we can combine them using
SimpleSequentialChain .

from langchain.chains import SimpleSequentialChain

overall_chain = SimpleSequentialChain(
chains=[chain_one, chain_two],
verbose=True)

A couple of things to note:

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 12/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

We need not explicitly pass input_variables and output_variables for


SimpleSequentialChain as the underlying assumption is that the output from
chain 1 is passed as input to chain 2.

Finally, we can run it with the same math problem as before:

question = "If my age is half of my dad's age and he is going to be 60 next yea
overall_chain.run(question)

# OUTPUT
# > Entering new SimpleSequentialChain chain...

# > Entering new AgentExecutor chain...


# I need to figure out my dad's current age and then divide it by two.
# Action: PAL-MATH
# Action Input: What is my dad's current age if he is going to be 60 next year?
# Observation: 59
# Thought: I now know my dad's current age, so I can divide it by two to get my
# Action: Divide 59 by 2
# Action Input: 59/2
# Observation: Divide 59 by 2 is not a valid tool, try another one.
# Thought: I need to use PAL-MATH to divide 59 by 2.
# Action: PAL-MATH
# Action Input: Divide 59 by 2
# Observation: 29.5
# Thought: I now know the final answer.
# Final Answer: My current age is 29.5 years old.

# > Finished chain.


# My current age is 29.5 years old.

# Given your age, a great gift would be something that you can use and enjoy no

# > Finished chain.

# '\nGiven your age, a great gift would be something that you can use and enjoy

There might be times when you need to pass along some additional context to the
second chain, in addition to what it is receiving from the first chain. For instance, I

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 13/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

want to set a budget for the gift, depending on the age of the person that is returned
by the first chain. We can do so using SimpleMemory .

First, let’s update the prompt for chain_two and pass to it a second variable called
budget inside input_variables .

template = """You are a gift recommender. Given a person's age,\n


it is your job to suggest an appropriate gift for them. If age is under 10,\n
the gift should cost no more than {budget} otherwise it should cost atleast 10

Person Age:
{output}
Suggest gift:"""
prompt_template = PromptTemplate(input_variables=["output", "budget"], template
chain_two = LLMChain(llm=llm, prompt=prompt_template)

If you compare the template we had for SimpleSequentialChain with the one above,
you’ll notice that I have also updated the first input’s variable name from age →
output . This is a crucial step, failing which an error would be raised at the time of
chain validation — Missing required input keys: {age}, only had {input, output,

budget} .

This is because the output from the first entity in the chain (i.e. agent ) will be the
input for the second entity in the chain (i.e. chain_two ) and therefore the variable
names must match. Upon inspecting agent ’s output keys, we see that the output
variable is called output , hence the update.

print(agent.agent.llm_chain.output_keys)

# OUTPUT
["output"]

Next, let’s update the kind of chain we are making. We can no longer work with
SimpleSequentialChain because it only works in cases where this is a single input and
single output. Since chain_two is now taking two input_variables , we need to use
SequentialChain which is tailored to handle multiple inputs and outputs.

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 14/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

overall_chain = SequentialChain(
input_variables=["input"],
memory=SimpleMemory(memories={"budget": "100 GBP"}),
chains=[agent, chain_two],
verbose=True)

A couple of things to note:

Unlike SimpleSequentialChain , passing input_variables parameter is mandatory


for SequentialChain . It is a list containing the name of the input variables that
the first entity in the chain (i.e. agent in our case) expects.
Now some of you may be wondering how to know the exact name used in the
input prompt that the agent is going to use. We certainly did not write the
prompt for this agent (as we did for chain_two )! It's actually pretty
straightforward to find it out by inspecting the prompt template of the llm_chain

that the agent is made up of.

print(agent.agent.llm_chain.prompt.template)

# OUTPUT
#Answer the following questions as best you can. You have access to the followi

#PAL-MATH: A language model that is really good at solving complex word math pr

#Use the following format:

#Question: the input question you must answer


#Thought: you should always think about what to do
#Action: the action to take, should be one of [PAL-MATH]
#Action Input: the input to the action
#Observation: the result of the action
#... (this Thought/Action/Action Input/Observation can repeat N times)
#Thought: I now know the final answer
#Final Answer: the final answer to the original input question

#Begin!

#Question: {input}
#Thought:{agent_scratchpad}

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 15/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

As you can see toward the end of the prompt, the questions being asked by the end-
user is stored in an input variable by the name input . If for some reason you had to
manipulate this name in the prompt, make sure you are also updating the
input_variables at the time of the creation of SequentialChain .

Finally, you could have found out the same information without going through the
whole prompt:

print(agent.agent.llm_chain.prompt.input_variables)

# OUTPUT
# ['input', 'agent_scratchpad']

SimpleMemory is an easy way to store context or other bits of information that


shouldn’t ever change between prompts. It requires one parameter at the time of
initialization — memories . You can pass elements to it in dict form. For instance,
SimpleMemory(memories={“budget”: “100 GBP”}) .

Finally, let’s run the new chain with the same prompt as before. You will notice, the
final output has some luxury gift recommendations such as weekend getaways in
accordance with the higher budget in our updated prompt.

overall_chain.run("If my age is half of my dad's age and he is going to be 60 n

# OUTPUT
#> Entering new SequentialChain chain...

#> Entering new AgentExecutor chain...


# I need to figure out my dad's current age and then divide it by two.
#Action: PAL-MATH
#Action Input: What is my dad's current age if he is going to be 60 next year?
#Observation: 59
#Thought: I now know my dad's current age, so I can divide it by two to get my
#Action: Divide 59 by 2
#Action Input: 59/2
#Observation: Divide 59 by 2 is not a valid tool, try another one.
#Thought: I can use PAL-MATH to divide 59 by 2.
#Action: PAL-MATH
#Action Input: Divide 59 by 2
#Observation: 29.5

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 16/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

#Thought: I now know the final answer.


#Final Answer: My current age is 29.5 years old.

#> Finished chain.

# For someone of your age, a good gift would be something that is both practica

#> Finished chain.

For someone of your age, a good gift would be something that is both practical

Conclusion
Hopefully, the learnings I have shared through this post have made you more
comfortable in taking a deep dive into the library. This article just scratched the
surface, there is so much more to cover. For instance, how to build a QnA chatbot
over your own datasets, and how to optimize memory for these chatbots so that you
can cherry-pick/summarize conversations to send in the prompt rather than
sending all previous chat history as part of the prompt.

As always if there’s an easier way to do/explain some of the things mentioned in this
article, do let me know. In general, refrain from unsolicited destructive/trash/hostile
comments!

Until next time ✨

I enjoy writing step-by-step beginner’s guides, how-to tutorials, decoding terminology used
in ML/AI, etc. If you want full access to all my articles (and others on Medium), then you
can sign up using my link here.

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 17/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Step by step guide to explaining your ML project during a data


science interview.
With a bonus sample script at the end that lets you show off your
tech skills discreetly!
towardsdatascience.com

Time Series Modeling using Scikit, Pandas, and Numpy


Intuitive use of seasonality to improve model accuracy.
towardsdatascience.com

Hands-On Introduction to Github Actions for Data Scientists


Learn how to automate experiment tracking with Weights & Biases,
unit testing, artifact creation, and lots more…
towardsdatascience.com

Deploying an End to End Deep Learning Project with few clicks:


Part 2
Taking model from Jupyter notebook to Flask app, testing API
endpoint using Postman, and Heroku deployment
towardsdatascience.com

Large Language Models Langchain NLP Deep Dives Artificial Intelligence

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 18/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Follow

Written by Dr. Varshita Sher


3.8K Followers · Writer for Towards Data Science

Senior Data Scientist | Explain like I am 5 | Oxford & SFU Alumni | https://podurama.com | Top writer on
Medium

More from Dr. Varshita Sher and Towards Data Science

Dr. Varshita Sher in Towards Data Science

Exploring GEMBA: A New LLM-Based Metric for Translation Quality


Assessment
Using LLMs for evaluating translation quality

· 9 min read · Sep 30

228 2

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 19/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Damian Gil in Towards Data Science

Mastering Customer Segmentation with LLM


Unlock advanced customer segmentation techniques using LLMs, and improve your clustering
models with advanced techniques

24 min read · Sep 27

3.3K 26

Adrian H. Raudaschl in Towards Data Science

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 20/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Forget RAG, the Future is RAG-Fusion


The Next Frontier of Search: Retrieval Augmented Generation meets Reciprocal Rank Fusion
and Generated Queries

· 10 min read · Oct 6

1.6K 22

Dr. Varshita Sher in Towards Data Science

Understanding Python imports, __init__.py and pythonpath — once and


for all
Learn how to import packages and modules (and the difference between the two)

· 12 min read · Oct 7, 2021

1.3K 24

See all from Dr. Varshita Sher

See all from Towards Data Science

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 21/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Recommended from Medium

gil fernandes

LangChain Chat with Custom Tools, Functions and Memory


In this story we are going to explore how you can create a simple web based chat application
that communicates with a private REST API…

7 min read · Jul 11

31 1

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 22/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Lawrence Knight in Dev Genius

Build your First Conversational Document Retrieval Agent using


LangChain
A step-by-step guide to building a LangChain enabled conversational document retrieval
agent.

5 min read · Aug 18

41

Lists

Natural Language Processing


746 stories · 336 saves

AI Regulation
6 stories · 160 saves

ChatGPT prompts
27 stories · 541 saves

ChatGPT
21 stories · 217 saves

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 23/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Onkar Mishra in Artificial Intelligence in Plain English

Using Chains and Agents for LLM application development


Step by step guide to use chains and agents in langchain

16 min read · Aug 2

398 1

Vikas Tiwari in GoPenAI

Langchain Agent Tools for Functions and APIs


https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 24/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

In the world of software development, we often find ourselves working with multiple functions,
each serving a different purpose or…

5 min read · Jul 9

Mastering LLM (Large Language Model)

Mastering ReAct Prompting: A Crucial Step in LangChain


Implementation — A Guided Example for Agents
Don’t rush into agent applications in LangChain. First, grasp the essence of ReAct Prompting
with our guided example. Lay the foundation…

11 min read · Sep 16

19

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 25/26
10/26/23, 5:26 PM A Gentle Intro to Chaining LLMs, Agents, and utils via LangChain | by Dr. Varshita Sher | Towards Data Science

Matt Tengtrakool in Artificial Corner

How to build tool-using agents with LangChain


Learn to use LangChain and Pinecone to build LLM agents that can access the internet and
knowledge bases

6 min read · Jun 4

217 3

See more recommendations

https://towardsdatascience.com/a-gentle-intro-to-chaining-llms-agents-and-utils-via-langchain-16cd385fca81 26/26

You might also like