# The JSTL Expression Language

This chapter is from the book

## 2.4 Operators

JSTL offers a small set of operators, listed in Table 2.1.

#### Table 2.1 Expression Language Operators

 Type Operators Arithmetic + - * / (div) % (mod) Grouping () Identifier Access . [] Logical && (and) || (or) ! (not) empty Relational == (eq) != (ne) < (lt) > (gt) <= (le) >= (ge) Unary -

You need to know three things about the operators in Table 2.1. First, you need to know the operators' syntax; for example, the + operator is used like this: A + B. That material is not covered here because you use EL expressions just like you use their Java equivalents. The second thing you need to know is operator precedence, so you can deduce that 1 + 3 * 5 is 16 but (1 + 3) * 5 is 20. Operator precedence is discussed in "Operator Precedence" on page 45. The third thing you need to know about the operators listed in Table 2.1 is what data types they prefer and how the EL performs type coercion. The former is briefly discussed here and the latter is discussed in "Type Coercion" on page 62.

All of the binary arithmetic operations prefer Double values and all of them will resolve to 0 if either of their operands is null. The operators + - * % will try to coerce their operands to Long values if they cannot be coerced to Double.

The grouping operators, which are parentheses, can be used to force operator precedence, as discussed above. The identifier access operators are discussed in "The . and [] Operators" on page 45, so that discussion is not repeated here.

The relational operators all have textual equivalents; for example, either == or eq will suffice for the equality operator. Those equivalents are provided for XML generation. Like binary arithmetic operations, all of the relational operators prefer Double values but will make do with Long values if the operands cannot be converted to Double.

The logical operators prefer to work with Boolean operands. You can use the empty operator to see if a value is either null or an empty string (""). That operator comes in handy when you are interpreting request parameters.

### Operator Precedence

The precedence for EL operators is listed below:

• [] .
• ()
• - (unary) not ! empty
• * / div % mod
• + - (binary)
• < > <= >= lt gt le ge
• == != eq ne
• && and
• || or =

The operators are listed above from left to right and top to bottom according to precedence; for example, the [] operator has precedence over the . operator, and the modulus (% or mod) operator, which represents a division remainder, has precedence over the logical operators.

### The . and [] Operators

The JSTL expression language provides two operators—. and []—that let you access scoped variables and their properties. The . operator is similar to the Java . operator, but instead of invoking methods, you access bean properties; for example, if you have a Name bean stored in a scoped variable named name and that bean contains firstName and lastName properties, you can access those properties like this:

```First Name: <c:out value='\${name.firstName}'/>
Last Name: <c:out value='\${name.lastName}'/>```

Assuming that there is a bean named name that has readable properties firstName and lastName in one of the four JSP scopes—meaning methods named getFirstName and getLastName—the preceding code fragment will display those properties.

You can also use the [] operator to access bean properties; for example, the preceding code fragment could be rewritten like this:

```First Name: <c:out value='\${name["firstName"]}'/>
Last Name: <c:out value='\${name["lastName"]}'/>```

The [] operator is a generalization of the . operator, which is why the two previous code fragments are equivalent, but the [] operator lets you specify a computed value. "A Closer Look at the [] Operator" on page 56 takes a closer look at how the [] operator works.

You can also use the[] operator to access objects stored in maps, lists, and arrays; for example, the following code fragment accesses the first object in an array:

```<% String[] array = { "1", "2", "3" };
pageContext.setAttribute("array", array); %>

<c:out value='\${array[0]}'/>```

The preceding code fragment creates an array of strings and stores it in page scope with a scriptlet. Subsequently, the <c:out> action accesses the first item in the array with \${array[0]}.

The following sections—"Accessing JavaBeans Components" and "Accessing Objects Stored in Arrays, Lists, and Maps" on page 52—explore in greater detail the use of the . and [] operators to access bean properties and objects stored in collections.

### Accessing JavaBeans Components

This section shows you how to use the . and [] operators to access bean properties, including nested beans. Listing 2.1, Listing 2.2, and Listing 2.3 list the implementation of three beans: Name, Address, and UserProfile.

#### Listing 2.1 WEB-INF/classes/beans/Name.java

```package beans;

public class Name {
private String firstName, lastName;

// JavaBean accessors for first name
public void setFirstName(String ´firstName) {
this.firstName = firstName;
}
public String getFirstName() {
return firstName;
}

// JavaBean accessors for last name
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getLastName() {
return lastName;
}
}```

```package beans;

private int zip;

// JavaBean accessors for street address
}
}

// JavaBean accessors for city
public void setCity(String city) {
this.city = city;
}
public String getCity() {
return city;
}
// JavaBean accessors for state
public void setState(String state) {
this.state = state;
}
public String getState() {
return state;
}

// JavaBean accessors for zip
public void setZip(int zip) {
this.zip = zip;
}
public int getZip() {
return zip;
}
}```

#### Listing 2.3 WEB-INF/classes/beans/UserProfile.java

```package beans;

public class UserProfile {
private Name name;

// JavaBean accessors for name
public void setName(Name name) {
this.name = name;
}
public Name getName() {
return name;
}

}
}
}```

The preceding beans are simple JavaBean components. The Name bean has two properties: firstName and lastName. The Address bean has four properties: streetAddress, city, state, and zip. The UserProfile bean has two properties: name and address. UserProfile beans contain references to Name and Address beans.

Figure 2–1 shows a JSP page that creates a user profile and accesses its properties with EL expressions.

Figure 2–1 Accessing Beans with the Expression Language

The JSP page shown in Figure 2–1 is listed in Listing 2.4.

#### Listing 2.4 Accessing JavaBean Properties

```<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<title>Accessing Beans with the EL</title>
<body>
<%@ taglib uri='http://java.sun.com/jstl/core' prefix='c' %>

<%-- Create a Name bean and store it in page scope --%>
<jsp:useBean id='name' class='beans.Name'>
<%-- Set properties with strings --%>
<jsp:setProperty name='name'
property='firstName' value='Claude'/>
<jsp:setProperty name='name'
property='lastName'  value='Loubier'/>
</jsp:useBean>

<%-- Create an Address bean and store it in page scope --%>
<%-- Set properties with strings --%>
value='119342 North Maison'/>
property='city'  value='Buffalo'/>
property='state' value='New York'/>
property='zip'   value='14214'/>
</jsp:useBean>

<%-- Create a UserProfile bean and store it in
page scope --%>
<jsp:useBean id='profile'
class='beans.UserProfile'>
<%-- Set properties with the name bean and address
bean stored in page scope --%>
<jsp:setProperty name='profile'
property='name'
value='<%= (beans.Name)
pageContext.getAttribute("name") %>'/>

<jsp:setProperty name='profile'
</jsp:useBean>

<%-- Show profile information --%>

Profile for
<%-- Access the name bean's firstName property directly,
without specifying scope --%>
<c:out value='\${name["firstName"]}'/>

<%-- Access the name bean's lastName property through the
profile bean by explicitly specifying scope --%>
<c:out value='\${pageScope.profile.name.lastName}'/>:
<p>
<table>
<tr>
<%-- Access the UserProfile bean's properties without
explicitly specifying scope --%>
<td>First Name:</td>
<td><c:out value='\${profile["name"].firstName}'/></td>
</tr><tr>
<td>Last Name:
<td><c:out value='\${profile.name["lastName"]}'/></td>
</tr><tr>
</td>
</tr><tr>
<td>City:
</tr><tr>
<td>State:
</tr><tr>
<td>Zip Code:
</tr>
</table>
</body>
</html>```

The preceding JSP page creates three beans: a name bean, an address bean, and a user profile bean; the name and address beans are used to create the user profile. All three beans are stored in page scope.

The JSP page listed in Listing 2.4 uses EL expressions to access properties of the user profile. First, the JSP page accesses the name bean's firstName property with the expression \${name["firstName"]}, which is equivalent to this expression: \${name.firstName}.

Next, the JSP page accesses the name bean's lastName property with this expression: \${pageScope.profile.name.lastName}. The expression starts with the pageScope identifier, which is an implicit object that provides access to all page-scoped attributes.8 The user profile bean—named profile—that exists in page scope is accessed by name with an identifier, and its enclosed name bean is also accessed with an identifier. Finally, the lastName property of that name bean is accessed with another identifier.

The rest of the JSP page accesses the profile bean's properties by using the . and [] operators. Remember that the . and [] operators are interchangeable when accessing bean properties, so the expression \${profile["name"]. firstName} is equivalent to \${profile.name.firstName} and \${profile.name["lastName"]} is equivalent to \${profile.name.lastName}.

Now that we've seen how to access bean properties, let's see how to access objects stored in arrays, lists, and maps.

### Accessing Objects Stored in Arrays, Lists, and Maps

In "Accessing JavaBeans Components" on page 46 we discussed a Web application that created user profiles and accessed their properties, all in a single JSP page. For a change of pace, this section discusses a Web application that creates user profiles in a servlet and accesses their properties in a JSP page.9 Figure 2–2 shows the Web application's JSP page.

Figure 2–2 Accessing Arrays, Lists, and Maps with the JSTL Expression Language

The JSP page shown in Figure 2–2 is accessed indirectly with the URL /dataCreator. That URL invokes a servlet that creates user profiles and forwards to the JSP page. Listing 2.5 lists the application's deployment descriptor, which maps the /dataCreator URL to the dataCreator servlet.

#### Listing 2.5 WEB-INF/web.xml

```<?xml version="1.0" encoding="ISO-8859-1"?>

<!DOCTYPE web-app
PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
"http://java.sun.com/j2ee/dtds/web-app_2.3.dtd">

<web-app>
<servlet>
<servlet-name>dataCreator</servlet-name>
<servlet-class>DataCreatorServlet</servlet-class>
</servlet>

<servlet-mapping>
<servlet-name>dataCreator</servlet-name>
<url-pattern>/dataCreator</url-pattern>
</servlet-mapping>
</web-app>	```

The dataCreator servlet is listed in Listing 2.6.

#### Listing 2.6 WEB-INF/classes/DataCreatorServlet.java

```import java.io.IOException;
import java.util.*;
import javax.servlet.*;
import javax.servlet.http.*;
import beans.*;

public class DataCreatorServlet extends HttpServlet {
public void doGet(HttpServletRequest request,
HttpServletResponse response)
throws IOException, ServletException {
// Create an array, map, and list
UserProfile[] profileArray = createProfiles();
HashMap         profileMap = new HashMap();

// Populate the list and map
for(int i=0; i < profileArray.length; ++i) {
UserProfile profile = profileArray[i];

String firstName = profile.getName().getFirstName(),
lastName = profile.getName().getLastName(),
key = firstName + " " + lastName;
profileMap.put(key, profile);
}

// Store the array, map, and list in request scope
request.setAttribute("profileArray", profileArray);
request.setAttribute("profileMap",   profileMap);
request.setAttribute("profileList",  profileList);

// Forward the request and response to /showData.jsp
RequestDispatcher rd =
getServletContext().getRequestDispatcher("/showData.jsp");

rd.forward(request, response);
}
private UserProfile[] createProfiles() {
// Create an array of user profiles
UserProfile[] userProfiles = {
new UserProfile(new Name("James", "Wilson"),
"New York", 14214)),
new UserProfile(new Name("Cindy", "Smith"),
"Buffalo", "New York", 14214))
};
return userProfiles;
}
}	```

The preceding servlet creates two user profiles and stores those profiles in an array, a map, and a list. Subsequently, the servlet stores the array, map, and list in request scope and forwards to a JSP page named showData.jsp. That JSP page is shown in Figure 2–2 and listed in Listing 2.7.

#### Listing 2.7 showData.jsp

```<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<title>Accessing Arrays, Lists, and Maps with the EL</title>
<body>
<%@ taglib uri='http://java.sun.com/jstl/core' prefix='c' %>

<%-- Access the first and last names stored in the two
user profiles through the array, list, and map --%>
Profiles are in request scope for <b>
<c:out value='\${profileArray[0].name.firstName}'/>
<c:out value='\${profileArray[0].name.lastName}'/></b>
and <b>
<c:out value='\${profileList[1].name.firstName}'/>
<c:out value='\${profileMap["Cindy Smith"].name.lastName}'/>
</b><p>

<%-- Store the two profiles in page-scoped variables --%>
<c:set var='jamesProfile'
value='\${profileMap["James Wilson"]}'/>

<c:set var='cindyProfile'
value='\${profileList[1]}'/>

<%-- Show address information, through the page-scoped
variables --%>
<c:out value='\${jamesProfile.name.firstName}'/> lives at:<b>

<p>

<c:out value='\${cindyProfile.name.firstName}'/> lives at:<b>

</body>
</html>	```

As the preceding JSP page illustrates, you access objects in an array with the [] operator, just as you would in Java by specifying a 0-based index into the array; for example, the expression \${profileArray[0].name.firstName} accesses the first name of the first profile stored in the profileArray.

You access objects stored in a list with the same syntax used for accessing objects in arrays; for example, in the preceding JSP page, the expression \${profileList[1].name.firstName} accesses the first name of the second profile stored in the profileList.

The Java class libraries offer quite a few different types of maps, including hash tables, hash maps, attributes, and tree maps. All of those data structures store key/value pairs of objects. To access those objects using the EL, you specify a key, enclosed in double quotes, with the [] operator; for example, the JSP page listed in Listing 2.7 accesses Cindy Smith's last name with this expression: \${profileMap["Cindy Smith"].name.lastName}.

As you can tell from the JSP pages listed in Listing 2.4 on page 49 and Listing 2.7, accessing nested bean properties can be rather verbose, although it's much more succinct than accessing properties with a JSP expression. You can reduce that verbosity by creating page-scoped variables that directly reference beans stored in

data structures. For example, the JSP page listed in Listing 2.7 stores James Wilson's user profile in a page-scoped variable named jamesProfile. That JSP page also creates a page-scoped variable named cindyProfile that directly references the user profile for Cindy Smith. Those page-scoped variables make it easier to access the user profiles; for example, instead of accessing Cindy's first name through the profile map like this: \${profileMap["Cindy Smith"].name.firstName}, you can access it like this: \${cindyProfile.name.firstName}.

In this and the preceding section, we discussed how to use the [] operator to access bean properties and beans stored in arrays, lists, and maps. In the next section, we take a closer look at how the [] operator works and why you might prefer that operator to the . operator when accessing beans.

### A Closer Look at the [] Operator

As discussed in "Accessing JavaBeans Components" on page 46 and "Accessing Objects Stored in Arrays, Lists, and Maps" on page 52, you use the [] operator with this syntax: \${identifier[subexpression]}. Here's how expressions with that syntax are evaluated:

1. Evaluate the identifier and the subexpression; if either resolves to null, the expression is null.

2. If the identifier is a bean: The subexpression is coerced to a String value and that string is regarded as a name of one of the bean's properties. The expression resolves to the value of that property; for example, the expression \${name.["lastName"]} translates into the value returned by name.getLastName().

3. If the identifier is an array: The subexpression is coerced to an int value—which we'll call subexpression-int—and the expression resolves to identifier[subexpression-int]. For example, for an array named colors, colors[3] represents the fourth object in the array. Because the subexpression is coerced to an int, you can also access that color like this: colors["3"]; in that case, JSTL coerces "3" into 3. That feature may seem like a very small contribution to JSTL, but because request parameters are passed as strings, it can be quite handy.

4. If the identifier is a list: The subexpression is also coerced to an int—which we will also call subexpression-int—and the expression resolves to the value returned from identifier.get(subexpression-int), for example: colorList[3] and colorList["3"] both resolve to the fourth element in the list.

5. If the identifier is a map: The subexpression is regarded as one of the map's keys. That expression is not coerced to a value because map keys can be any type of object. The expression evaluates to identifier.get(subexpression), for example, colorMap[Red] and colorMap["Red"]. The former expression is valid only if a scoped variable named Red exists in one of the four JSP scopes and was specified as a key for the map named colorMap.

Table 2.2 lists the methods that the EL invokes on your behalf.

#### Table 2.2 Methods That the EL Invokes for You

 Identifier Type Example Use Method Invoked JavaBean component \${colorBean.red} \${colorBean["red"]} colorBean.getRed() Array \${colorArray[2]} \${colorArray["2"]} Array.get(colorArray, 2) List colorList[2] colorList["2"] colorList.get(2) Map colorMap[red] colorMap["red"] colorMap.get(pageContext. findAttribute("red")) colorMap.get("red")

JSTL developers rely heavily on maps because the EL provides 11 indispensable implicit objects, of which 10 are maps. Everything, from request parameters to cookies, is accessed through a map. Because of this reliance on maps, you need to understand the meaning of the last row in Table 2.2. You access a map's values through its keys, which you can specify with the [] operator, for example, in Table 2.2, \${colorMap[red]} and \${colorMap["red"]}. The former specifies an identifier for the key, whereas the latter specifies a string. For the identifier, the PageContext.findAttribute method searches all four JSP scopes for a scoped variable with the name that you specify, in this case, red. On the other hand, if you specify a string, it's passed directly to the map's get method.

#### The [] Operator's Special Ability

Although it may not be obvious from our discussion so far, the [] operator has a special ability that its counterpart, the . operator, does not have—it can operate on an expression, whereas the . operator can only operate on an identifier. For example, you can do this: \${colorMap[param.selectedColor]}, which uses the string value of the selectedColor request parameter as a key for a map named colorMap.10 That's something that you can't do with the . operator.

Figure 2–3 shows a Web application that uses the [] operator's special ability to show request header values.

Figure 2–3 Illustrating an Advantage of the [] Operator

The top picture in Figure 2–3 shows a JSP page that lets you select a request header. After you activate the Show First Header Value button, the JSP page shown in the bottom picture shows the first value for the request header that was selected.

The JSP page shown in the top picture in Figure 2–3 is listed in Listing 2.8.

```Listing 2.8	Selecting a Request Header
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<title>Using the EL Generalized Access Operator</title>
<body>
<%@ taglib uri='http://java.sun.com/jstl/core' prefix='c' %>

Show the first value for this request header:

<option value='<c:out value="\${hdr.key}"/>'>
<c:out value='\${hdr.key}'/>
</option>
</c:forEach>
</select>

<p><input type='submit' value='Show First Header Value'/>
</form>
</body>
</html>	```

The preceding JSP page uses the header JSTL implicit object to iterate over request headers. The names of those request headers are used to create an HTML select element named headerName. The select element resides in a form whose action is show_first_header_value.jsp, so that the JSP page is loaded when you activate the Show First Header Value button. That JSP page is listed in Listing 2.9.

```Listing 2.9	Using the [] Operator with a Request Parameter
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<title>Using the EL Generalized Access Operator</title>
<body>
<%@ taglib uri='http://java.sun.com/jstl/core' prefix='c' %>

The first value for the header named <b>
</body>
</html>	```

The preceding JSP page uses two JSTL implicit objects: param, which is a map of request parameters, and header, which is a map of request headers. The subexpression param.headerName accesses the headerName request parameter's value, and the expression \${header[param.headerName]} resolves to the first value for that request header.

### The empty Operator

Testing for the existence of request parameters can be tricky because they evaluate to null if they don't exist but they evaluate to an empty string ("") if their value was not specified. Most of the time, when you check for the existence of request parameters, you don't have to distinguish the former from the latter; you just want to know whether a value was specified. For that special task, you can use the empty operator, which tests whether an identifier is null or doesn't exist, as illustrated by the Web application shown in Figure 2–4.

Figure 2–4 Using the empty Operator to Test for the Existence of Request Parameters

The Web application shown in Figure 2–4 consists of two JSP pages, one that lets you enter a name and another that checks for a corresponding request parameter. As illustrated by the top two pictures in Figure 2–4, if you don't enter anything in the name field, the latter JSP page prints an error message and includes the referring JSP page. The bottom two pictures illustrate successful access to the name request parameter. The JSP page with the name input field is listed in Listing 2.10.

#### Listing 2.10index.jsp

```<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<title>Using the Empty Operator</title>
<body>
<jsp:include page='form.jsp'/>
</body>
</html>	```

The preceding JSP page includes form.jsp, which is listed in Listing 2.11.

#### Listing 2.11 form.jsp

```<form action='check_header.jsp'>
Name: <input type='text' name='name'/>
<p><input type='submit' value='Register'/>
</form>	```

The action for the form in the preceding JSP page is check_header.jsp, which is listed in Listing 2.12.

```<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<title>Using the Empty Operator</title>
<body>
<%@ taglib uri='http://java.sun.com/jstl/core' prefix='c' %>

<c:choose>
<c:when test='\${not empty param.name}'>
Hello <c:out value='\${param.name}'/>.
</c:when>

<c:otherwise>
<font color='red'>
</font>

<jsp:include page='form.jsp'/>
</c:otherwise>
</c:choose>
</body>
</html>	```

The preceding JSP page combines the not and empty operators to see whether the name request parameter was specified; if so it displays a personalized greeting; otherwise, it prints an error message and includes the referring JSP page.

### InformIT Promotional Mailings & Special Offers

I would like to receive exclusive offers and hear about products from InformIT and its family of brands. I can unsubscribe at any time.

## Overview

Pearson Education, Inc., 221 River Street, Hoboken, New Jersey 07030, (Pearson) presents this site to provide information about products and services that can be purchased through this site.

This privacy notice provides an overview of our commitment to privacy and describes how we collect, protect, use and share personal information collected through this site. Please note that other Pearson websites and online products and services have their own separate privacy policies.

## Collection and Use of Information

To conduct business and deliver products and services, Pearson collects and uses personal information in several ways in connection with this site, including:

### Questions and Inquiries

For inquiries and questions, we collect the inquiry or question, together with name, contact details (email address, phone number and mailing address) and any other additional information voluntarily submitted to us through a Contact Us form or an email. We use this information to address the inquiry and respond to the question.

### Online Store

For orders and purchases placed through our online store on this site, we collect order details, name, institution name and address (if applicable), email address, phone number, shipping and billing addresses, credit/debit card information, shipping options and any instructions. We use this information to complete transactions, fulfill orders, communicate with individuals placing orders or visiting the online store, and for related purposes.

### Surveys

Pearson may offer opportunities to provide feedback or participate in surveys, including surveys evaluating Pearson products, services or sites. Participation is voluntary. Pearson collects information requested in the survey questions and uses the information to evaluate, support, maintain and improve products, services or sites, develop new products and services, conduct educational research and for other purposes specified in the survey.

### Contests and Drawings

Occasionally, we may sponsor a contest or drawing. Participation is optional. Pearson collects name, contact information and other information specified on the entry form for the contest or drawing to conduct the contest or drawing. Pearson may collect additional personal information from the winners of a contest or drawing in order to award the prize and for tax reporting purposes, as required by law.

If you have elected to receive email newsletters or promotional mailings and special offers but want to unsubscribe, simply email information@informit.com.

### Service Announcements

On rare occasions it is necessary to send out a strictly service related announcement. For instance, if our service is temporarily suspended for maintenance we might send users an email. Generally, users may not opt-out of these communications, though they can deactivate their account information. However, these communications are not promotional in nature.

### Customer Service

We communicate with users on a regular basis to provide requested services and in regard to issues relating to their account we reply via email or phone in accordance with the users' wishes when a user submits their information through our Contact Us form.

## Other Collection and Use of Information

### Application and System Logs

Pearson automatically collects log data to help ensure the delivery, availability and security of this site. Log data may include technical information about how a user or visitor connected to this site, such as browser type, type of computer/device, operating system, internet service provider and IP address. We use this information for support purposes and to monitor the health of the site, identify problems, improve service, detect unauthorized access and fraudulent activity, prevent and respond to security incidents and appropriately scale computing resources.

### Web Analytics

Pearson may use third party web trend analytical services, including Google Analytics, to collect visitor information, such as IP addresses, browser types, referring pages, pages visited and time spent on a particular site. While these analytical services collect and report information on an anonymous basis, they may use cookies to gather web trend information. The information gathered may enable Pearson (but not the third party web trend services) to link information with application and system log data. Pearson uses this information for system administration and to identify problems, improve service, detect unauthorized access and fraudulent activity, prevent and respond to security incidents, appropriately scale computing resources and otherwise support and deliver this site and its services.

This site uses cookies and similar technologies to personalize content, measure traffic patterns, control security, track use and access of information on this site, and provide interest-based messages and advertising. Users can manage and block the use of cookies through their browser. Disabling or blocking certain cookies may limit the functionality of this site.

### Do Not Track

This site currently does not respond to Do Not Track signals.

## Security

Pearson uses appropriate physical, administrative and technical security measures to protect personal information from unauthorized access, use and disclosure.

## Children

This site is not directed to children under the age of 13.

## Marketing

Pearson may send or direct marketing communications to users, provided that

• Pearson will not use personal information collected or processed as a K-12 school service provider for the purpose of directed or targeted advertising.
• Such marketing is consistent with applicable law and Pearson's legal obligations.
• Pearson will not knowingly direct or send marketing communications to an individual who has expressed a preference not to receive marketing.
• Where required by applicable law, express or implied consent to marketing exists and has not been withdrawn.

Pearson may provide personal information to a third party service provider on a restricted basis to provide marketing solely on behalf of Pearson or an affiliate or customer for whom Pearson is a service provider. Marketing preferences may be changed at any time.

## Correcting/Updating Personal Information

If a user's personally identifiable information changes (such as your postal address or email address), we provide a way to correct or update that user's personal data provided to us. This can be done on the Account page. If a user no longer desires our service and desires to delete his or her account, please contact us at customer-service@informit.com and we will process the deletion of a user's account.

## Choice/Opt-out

Users can always make an informed choice as to whether they should proceed with certain services offered by InformIT. If you choose to remove yourself from our mailing list(s) simply visit the following page and uncheck any communication you no longer want to receive: www.informit.com/u.aspx.

## Sale of Personal Information

Pearson does not rent or sell personal information in exchange for any payment of money.

While Pearson does not sell personal information, as defined in Nevada law, Nevada residents may email a request for no sale of their personal information to NevadaDesignatedRequest@pearson.com.

## Supplemental Privacy Statement for California Residents

California residents should read our Supplemental privacy statement for California residents in conjunction with this Privacy Notice. The Supplemental privacy statement for California residents explains Pearson's commitment to comply with California law and applies to personal information of California residents collected in connection with this site and the Services.

## Sharing and Disclosure

Pearson may disclose personal information, as follows:

• As required by law.
• With the consent of the individual (or their parent, if the individual is a minor)
• In response to a subpoena, court order or legal process, to the extent permitted or required by law
• To protect the security and safety of individuals, data, assets and systems, consistent with applicable law
• In connection the sale, joint venture or other transfer of some or all of its company or assets, subject to the provisions of this Privacy Notice
• To investigate or address actual or suspected fraud or other illegal activities
• To exercise its legal rights, including enforcement of the Terms of Use for this site or another contract
• To affiliated Pearson companies and other companies and organizations who perform work for Pearson and are obligated to protect the privacy of personal information consistent with this Privacy Notice
• To a school, organization, company or government agency, where Pearson collects or processes the personal information in a school setting or on behalf of such organization, company or government agency.

This web site contains links to other sites. Please be aware that we are not responsible for the privacy practices of such other sites. We encourage our users to be aware when they leave our site and to read the privacy statements of each and every web site that collects Personal Information. This privacy statement applies solely to information collected by this web site.