Movatterモバイル変換


[0]ホーム

URL:


— FREE Email Series —

🐍 Python Tricks 💌

Python Tricks Dictionary Merge

🔒 No spam. Unsubscribe any time.

Browse TopicsGuided Learning Paths
Basics Intermediate Advanced
aialgorithmsapibest-practicescareercommunitydatabasesdata-sciencedata-structuresdata-vizdevopsdjangodockereditorsflaskfront-endgamedevguimachine-learningnewsnumpyprojectspythonstdlibtestingtoolsweb-devweb-scraping

Table of Contents

How to Join Strings in Python

How to Join Strings in Python

byMartin BreussReading time estimate 25mbasicspython

Table of Contents

Remove ads

Python’s built-in string method.join() lets you combine string elements from an iterable into a single string, using a separator that you specify. You call.join() on the separator, passing the iterable of strings to join.

By the end of this tutorial, you’ll understand that:

  • You use.join() in Python tocombine string elements with aspecified separator.
  • Aseparator is the piece of text you wantinserted between each substring.
  • To join list elements, youcall.join() on a separator string, passing the list as the argument.
  • .join()inserts the separator between each list element to form a single string.
  • The.join() methodreturns a new string that is the concatenation of the elements in the iterable, separated by the specified string.
  • For smaller string concatenation tasks, you can use theconcatenation operator (+) orf-strings instead of.join().

Python’s built-instr.join() method gives you a quick and reliable way to combine multiple strings into a single string. Whether you need to format output or assemble data for storage,.join() provides a clean and efficient approach for joining strings from aniterable.

In the upcoming sections, you’ll learn the basic usage of.join() to concatenate strings effectively. You’ll then apply that knowledge to real-world scenarios, from building CSV files to constructing custom log outputs. You’ll also discover some surprising pitfalls and learn how to avoid them.

Get Your Code:Click here to download the free sample code that shows you how to join strings in Python.

Take the Quiz: Test your knowledge with our interactive “How to Join Strings in Python” quiz. You’ll receive a score upon completion to help you track your learning progress:


How to Join Strings in Python

Interactive Quiz

How to Join Strings in Python

Test your understanding of Python's .join() string method for combining strings, handling edge cases, and optimizing performance.

How to Join Strings in Python Using.join()

To use the string method.join(), you call.join() on a separator string and pass aniterable of other strings as the argument. The method returns a single string, where it has inserted the separator string between each element of the iterable:

Python
>>>words=["Time","flies","like","an","arrow!"]>>>" ".join(words)'Time flies like an arrow!'

In this example, you joined a list of words into one sentence, separated by spaces.

At first glance, this usage might look a little backward. In many otherstring operations, you call the method on the main string that you want to manipulate. However, with.join(), you call the method on the separator string, then pass the iterable of strings that you want to combine:

Python
>>>separator=" ">>>separator.join(words)'Time flies like an arrow!'

This example achieves the same result as the earlier one but splits the process into two steps. Definingseparator separately makes the code more readable and avoids the potentially odd-looking syntax of calling.join() directly on a short string literal.

Note: Remember that.join() is astring method, which means that you’ll need to call it on asingle string object. Keeping that in mind may help you remember why you need to call it on the separator string.

You rarely see code that’s written in multiple steps where you assign the separator string to a variable, like you did in the example above.

In typical usage, you call.join() directly on the separator string, all in one line. This approach is more concise and highlights that any valid string can be your separator, whether it’s whitespace, a dash, or a multicharacter substring.

Join With an Empty String

What if you don’t want any separator at all, but just want toconcatenate the items? One valid approach is to use an empty string ("") as the separator:

Python
>>>letters=["A","B","C","D"]>>>"".join(letters)'ABCD'

This code snippet concatenates the letters in the list, forming a single string"ABCD". Using an empty string as the separator is a great way to assemble strings without a delimiter between them.

Combine Strings of Characters

Since.join() can take any iterable of strings—not just lists—you can even pass a string as an argument. Because strings are iterable, Python iterates over each character in that string, considering each character as a separate element:

Python
>>>characters="ABCD">>>",".join(characters)'A,B,C,D'

By calling.join() on"," and passing the stringcharacters, you effectively place a comma between every single character in"ABCD". This might not always be what you intend, but it’s a neat trick to keep in mind if you ever need to treat each character as a separate element.

Next, you’ll continue to explore using different separators when joining strings with.join().

Join Elements of an Iterable With Specific Separators

In many real-world scenarios, you’ll want to join data with a specific delimiter. For example, when creating rows of CSV data, you could join all row elements using a single comma. Or, when you’re preparing data for display, you may want to use a tab character to make it more readable.

Create Comma-Delimited Output

Suppose you have a list of fruit names that you want to pack into a single string with each fruit separated by a comma. You can handle this in one line:

Python
>>>fruits=["apple","orange","lemon","kiwi"]>>>csv_line=",".join(fruits)>>>print(csv_line)apple,orange,lemon,kiwi

If you save or print this data to a file, you can handle it as a line in a basic CSV format. This approach is quick and efficient. However, keep in mind that if you need to handle quotes or complex CSV structures, then you should usePython’s dedicatedcsv library.

Collapse a List of URL Parts

Another use case for.join() is constructing or normalizing URL paths. Often, you’ll have a base domain and a list of subpaths that you want to concatenate with a slash (/):

Pythonurl_builder.py
base_url="https://example.com/"subpaths=["blog","2025","02","join-string"]full_url=base_url+"/".join(subpaths)print(full_url)

In this snippet, you start with a base URL, then use"/".join() to handle the rest.When you run the script, you’ll get a fully-formed URL as output:

Shell
$pythonurl_builder.pyhttps://example.com/blog/2025/02/join-string

If you need to handle more advanced URL operations, then you can also usePython’surllib library, specificallytheparse module, for robust URL manipulation.

Use Multicharacter Separators

Your separator doesn’t have to be a single character. You can also call.join() on a longer string if the delimiter you want has more than one character:

Python
>>>colors=["red","green","blue"]>>>" | ".join(colors)'red | green | blue'

This code snippet uses the three-character string" | " as a delimiter.

Such a use case might make your output more visually appealing or help you parse the string quicker by picking a unique delimiter.

Because.join() doesn’t place any restrictions on the separator’s length or content, you’re free to choose any delimiter that best suits your data and user-facing output:

Python
>>>running_instructions=("ready","set","go")>>>"...".join(running_instructions)'ready...set...go'

Joining values with.join() is one of the cleanest ways to convert a list of strings into a single output string. By calling.join() on the delimiter that you need—whether it’s a single character, a multicharacter substring, or even an empty string—you can unify your data in a single step.

Detangle Surprising Errors When Using.join()

You may occasionally run into surprising issues when attempting to join strings with.join(). Some common mistakes include mixing data types, or calling.join() on the main string instead of the separator. In this section, you’ll take a look at these pitfalls to save you time debugging.

Non-String Values in the Iterable

The most common error you’ll encounter when using.join() is aTypeError caused by trying to join an iterable that contains non-string values, such asintegers or floats:

Python
>>>countdown=[3,2,1]>>>"-".join(countdown)Traceback (most recent call last):...TypeError:sequence item 0: expected str instance, int found

Python complains that the first element is an integer, not a string. The.join() method only works with strings, and it won’t automatically convert values to strings for you.

If you’re confronted with a situation where you want to join objects that aren’t strings, you can explicitly convert each element to a string beforehand using alist comprehension or agenerator expression andstr():

Python
>>>countdown=[3,2,1]>>>"-".join(str(number)fornumberincountdown)'3-2-1'

Alternatively, you can use a morefunctional style with Python’smap() function:

Python
>>>countdown=[3,2,1]>>>"-".join(map(str,countdown))'3-2-1'

Both approaches ensure that the resulting iterable you pass to.join() consists only of strings. Without these explicit conversions, Python willraise aTypeError because.join() doesn’t transform objects into strings automatically.

Non-Iterable Types

You can only pass an iterable object as an argument to.join(). If you pass a non-iterable object, such asNone or an integer, then Python will raise an error:

Python
>>>"-".join(42)Traceback (most recent call last):...TypeError:can only join an iterable

Here, Python complains that42 isn’t an iterable, so.join() can’t loop over it and Python raises aTypeError.

If you’ve successfully done something like",".join("ABCD") in the past—passing a single string to.join()—then you might assume that passing just one integer or float would work the same way. A string may look like a single value, but Python treats it as asequence of characters, which means that it’s iterable.

Numbers, on the other hand, don’t implement theiterable protocol. As a result, passing them as arguments to.join() causes Python to raise aTypeError.

.join() Called on the Wrong Object

When you’re used to calling methods like.split() on the main string, it can feel counterintuitive that you need to call.join() on theseparator. When you accidentally reverse that order, you’ll get an unexpected result:

Python
>>>"Hello World!".join(",")','

In this snippet, you’re calling.join() on"Hello World!", but passing just"," as the iterable. A string is an iterable of its characters, so.join() will attempt to place the separator string"Hello World!" in between every character of the"," string.

However, that string only consists of a single character, so there’s no place to insert the separator. Therefore,.join() returns a new string that only consists of",". This result may be surprising!

If you want to insert a single comma between each of the characters that make up the string"Hello, World!", then you need to swap the order of the strings involved:

Python
>>>",".join("Hello World!")'H,e,l,l,o, ,W,o,r,l,d,!'

This confusion is especially common when you’re passing a single string as the argument to.join(), like in the example above. It’s a good idea to double-check that you always use"sep".join(iterable_of_strings) rather than accidentally reversing the order.

By understanding these pitfalls, you can avoid common mistakes when using.join(). Whether it’s converting non-string types or passing the correct iterable, a little awareness can save you time and frustration while debugging.

Consider the + Operator or F-Strings for Simple Scenarios

In some cases, you may not need to use.join(), like when you’re only concatenating a small number of strings. For example, using the plus operator (+) or f-strings might do just fine:

Python
 1>>>first_name="Kai" 2>>>last_name="Nguyen" 3 4>>>first_name+" "+last_name 5'Kai Nguyen' 6>>>f"{first_name}{last_name}" 7'Kai Nguyen'

The example above shows two different ways to create a new, larger string from the stringsfirst_name andlast_name:

For short examples like this, both approaches are often more readable than using.join():

Python
>>>" ".join([first_name,last_name])'Kai Nguyen'

All three ways work and produce the same output, but if you’re only joining a few strings, then it’s best to focus on readability and use an f-string.

For large tasks or in loops,.join() remains more efficient and expressive. Its true power becomes evident when you have a list or other iterable of unknown length, or when you’re dealing with hundreds or thousands of strings. In these scenarios,.join() is the tool of choice for writingPythonic code.

Create an Event Log String: Practical Example

At this point, you’ve learned how to use.join() with short toy examples. Now it’s time to tie everything together with a small real-world use case.

Imagine that you have access to JSON event logs from an application. Each key is a timestamp and the value is a list of event names with a varying amount of elements. You want to build a single, human-readable string from it that contains all your events in chronological order:

JSONevent_log.json
{"2025-01-24 10:00":["click","add_to_cart","purchase"],"2025-01-24 10:05":["click","page_view"],"2025-01-24 10:10":["page_view","click","add_to_cart"]}

You decide to create an output string with one line per timestamp. On each line, you want a comma-separated list of event names, prefixed by the timestamp. Using.join(), you can elegantly handle the formatting:

Pythonformat_event_log.py
 1importjson 2 3defload_log_file(file_path): 4withopen(file_path,mode="r",encoding="utf-8")asfile: 5returnjson.load(file) 6 7defformat_event_log(event_log): 8lines=[] 9fortimestamp,eventsinevent_log.items():10# Convert the events list to a string separated by commas11event_list_str=", ".join(events)12# Create a single line string13line=f"{timestamp} =>{event_list_str}"14lines.append(line)1516# Join all lines with a newline separator17return"\n".join(lines)1819if__name__=="__main__":20log_file_path="event_log.json"21event_log=load_log_file(log_file_path)22output=format_event_log(event_log)23print(output)

Runningformat_event_log.py produces readable output, formatted to your liking:

Shell
$pythonformat_event_log.py2025-01-24 10:00 => click, add_to_cart, purchase2025-01-24 10:05 => click, page_view2025-01-24 10:10 => page_view, click, add_to_cart

This example demonstrates how.join() helps you at multiple stages of the process—and also when it’s better to opt for a different approach when you need to concatenate strings:

  • Line 11 uses.join() to combine individual events with a comma separator.

  • Line 13 uses an f-string to assemble each line of the output. Because there are always only two variables to combine, the f-string is more readable than using.join().

  • Line 17 uses.join() another time to unify all lines into one final string with a newline separator between each line.

Your data remains readable and it’s straightforward to parse. Using.join() for string concatenation helps keep your code flexible and explicit about how each part of the output is structured. It also allows the implementation to grow and stay performant, even when handling a large number of log events per timestamp.

If you want to store the output in a text file for further analysis, then you can adapt the final step bywriting the output to a file:

Pythonformat_event_log.py
# ...if__name__=="__main__":log_file_path="event_log.json"event_log=load_log_file(log_file_path)output=format_event_log(event_log)withopen("event_log.txt",mode="w",encoding="utf-8")asfile:file.write(output)

That’s it! You’ve built a readable string from multiple parts using.join(). This example highlights how beneficial.join() can be for real-world text processing tasks.

If you’re curious about how.join() manages to do its work so efficiently, and you don’t mind peeking at CPython’s source code, then keep reading the next section.

Understand Howstr.join() Optimizes String Concatenation

So far, you’ve learned that.join() is efficient and useful when you need to join a large amount of strings. But why is that, and why are the other approaches that you’ve seen less performant?

When you build a string by repeatedly adding to it—such as using+= in a loop—each operation creates a new string and copies the existing data. This can lead to a quadratic-time cost if you have many strings or large data. In contrast,.join() makes two passes over your data and does only a single allocation. This makes it faster and more memory-friendly when you’re combining many substrings.

In this section, you’ll take a dip intoCPython’s source code to better understand how.join() manages to join strings without much overhead.

Pre-Pass: Check Types and Calculate Needed Space

Before doing any other work,CPython performs apre-pass that accomplishes two things:

  1. Type Check: It checks whether all elements are strings.
  2. Space Allocation: It calculates the total size of all items in the iterable, including the cumulative size of the separator, to create a new string with exactly the right size to fit all the pieces.

You can check out the actual implementation in the CPython source code in theunicodeobject.c file. There, you can find a function named_PyUnicode_JoinArray() that handles the low-level logic forPyUnicode_Join().

Below is a simplified snippet that shows the type check, and how the function calculates the total required size for the final joined string:

C
 1sz=0; 2seqlen=PySequence_Fast_GET_SIZE(seq); 3items=PySequence_Fast_ITEMS(seq); 4 5for(i=0;i<seqlen;i++){ 6item=items[i]; 7if(!PyUnicode_Check(item)){ 8/* If an element isn't a string, handle the error */ 9}10Py_ssize_titemlen=PyUnicode_GET_LENGTH(item);11sz+=itemlen;12}13if(seqlen>1){14sz+=seplen*(seqlen-1);15}

Remember that this is a simplified version of the original CPython code. You won’t find it just like this in the source code, but you can search for the variable names used above to see how they fit into the actual implementation.

Understanding what this code snippet does, however, can help when reading the actual source code:

  • Line 1 defines the variablesz, short forsize, and sets it to0. You’ll update this variable to store the length of the final string that the join operation will produce.

  • Lines 2 and 3 use specialized CPython functions to determine the size and collect the elements of the iterableseq. Note thatseq isn’t defined in the simplified code snippet above, but you’ll find it as a parameter in the original function in the source code.

  • Lines 5 to 12 make up a loop that iterates over the items ofseq, checks whether they’re valid strings that CPython can concatenate, calculates the length of each element, and adds that length tosz, incrementing it accordingly.

  • Lines 13 to 15 conditionally add the length of all necessary separators tosz. Because.join() adds the separator in between elements, you’ll needseqlen - 1 separators. This calculation is only relevant if there’s more than one item inseq and if you used a separator that’s larger than0 characters. Note that the simplified code snippet uses the variableseplen, which exists in the source code but isn’t defined above.

Using a similar but significantly more sophisticated approach, the real_PyUnicode_JoinArray() function determines the size of the string that the join operation will build. And because the runtime knows the total size (sz) beforehand, it can allocateexactly the required space for the final output when creating the initially empty, new string elementres:

C
/* ... */res=PyUnicode_New(sz,maxchar);

Creating a new object with the exact size requirements sets the stage for why.join() can be so efficient when you need to concatenate many items.

Second Pass: Copy Once and Insert Separators

After allocating the memory, CPython copies each string into the final buffer in order, inserting the separator as needed. Because of the setup work done during the pre-pass, it does this without needing to constantly re-create new objects.

Below you’ll find another simplified excerpt of the relevant CPython source code that you can study to better understand the high-level logic in_PyUnicode_JoinArray():

C
 1/* ... */ 2 3res_data=PyUnicode_1BYTE_DATA(res); 4sep_data=PyUnicode_1BYTE_DATA(sep); 5 6for(i=0;i<seqlen;i++){ 7item=items[i]; 8Py_ssize_titemlen=PyUnicode_GET_LENGTH(item); 9memcpy(res_data,10PyUnicode_DATA(item),11itemlen);12res_data+=itemlen;1314if(i<seqlen-1){15memcpy(res_data,16sep_data,17seplen);18res_data+=seplen;19}20}

Again, you won’t find this simplified code snippet in CPython’s source code, but it can be helpful to better understand the process that makes.join() efficient.

Assume that the variables from the previous step,res,sep,items,seqlen, andseplen are still accessible in this code:

  • Line 3 creates apointer to the raw data buffer ofres. CPython later uses this value to keep track of where to insert the data.

  • Line 4 does the same for the separator,sep. CPython uses this pointer to insert the separator’s data into the new string.

  • Line 6 starts a loop that iterates over each item,line 7 fetches the current item, andline 8 calculates its length again.

  • Lines 9 to 11 usememcpy() to insert the item’s data into the correct location inres, using theres_data pointer as the destination anditemlen to determine the size.

  • Line 12 advances theres_data pointer by the length of the item.

  • Line 14 checks whether you still need a separator, because you don’t need to add a separator after the last item of the iterable.

  • Lines 15 to 19 then insert the separator, again usingmemcpy(), and advance the pointer accordingly.

After this pass over the elements in the iterable,res contains the data of all the elements interspersed with as many separators as necessary.

Note: The actual source code of_PyUnicode_JoinArray() has a more complicated implementation that handles edge cases, such as empty separator strings and empty iterables, and throws errors where necessary.

Using this two-step approach, CPython only needs to create one new string, removing the cost of making multiple partial copies. Further, becauseres is already the right size, CPython can directly copy each piece into the final position.

Compare.join() to Using+= in a Loop

Now, consider using theaugmented concatenation operator (+=) inside afor loop as another approach to joining strings:

Pythonplus_loop_concatenation.py
cities=["Hanoi","Adelaide","Odessa","Vienna"]separator="->"travel_path=""fori,cityinenumerate(cities):travel_path+=cityifi<len(cities)-1:travel_path+=separatorprint(travel_path)

Here, each iteration needs to reallocate the result string,travel_path, to a new string object, copying previous data again and again. This results in a worst-case O(n²)time complexity.

Note: In this case, the augmented concatenation operator (+=) has the same effect on time complexity as if you used the concatenation operator (+):

Python
# ...travel_path=travel_path+city# ...

That’s because strings are immutable, and both operations will create a new string before assigning it back to the target name.

The.join() method, on the other hand, runs in roughly O(n), because it examines all items first to calculate the total length, allocates once, then copies each substring and separator exactly once. Additionally, the code looks a lot more readable:

Pythonjoin_concatenation.py
cities=["Hanoi","Adelaide","Odessa","Vienna"]travel_path="->".join(cities)print(travel_path)

The code injoin_concatenation.py produces the same result as the code inplus_loop_concatenation.py. But it’s also more straightforwardand more performant and scalable!

For a few short concatenations, you can use+, or f-strings. But once you’re handling an iterable of unknown length or find yourself joining strings in a loop,.join() remains the preferred andPythonic approach.

Conclusion

Python’s built-in.join() method is a powerful solution for assembling an iterable of strings into a single string. It’s more expressive and often more efficient than repeatedly using the plus operator, especially when you’re working with many pieces of text. Whether you’re formatting user output, generating CSV lines, or constructing custom logs,.join() offers a clean, Pythonic way to handle string concatenation.

In this tutorial, you learned how to:

  • Use.join() tocombine a list of strings into one
  • Join on different delimiters such as commas, spaces, slashes, or even empty strings
  • Handle commonpitfalls, such asattempting to join non-string data
  • Write code for areal-world scenario building user-facing logs with.join()
  • Dive deeper intoCPython source code to understand how.join()optimizes the concatenation process

With all of this in mind, you’re now well-equipped to bring together all your text data using Python. What a happy reunion! To continue honing your string manipulation skills, you can check out how tosplit strings in Python with.split() for handling incoming data. Additionally, you can use.strip() to remove unwanted characters, and.replace() to swap out characters as needed.

As you keep working with text data, you’ll discover that.join() is a helpful method for building maintainable code that gracefully handles string concatenation.

Get Your Code:Click here to download the free sample code that shows you how to join strings in Python.

Frequently Asked Questions

Now that you have some experience with joining strings using.join() in Python, you can use the questions and answers below to check your understanding and recap what you’ve learned.

These FAQs are related to the most important concepts you’ve covered in this tutorial. Click theShow/Hide toggle beside each question to reveal the answer.

You use.join() to concatenate an iterable of strings into a single string, inserting a separator string between each element of the iterable.

The string method.join() returns a new string element that’s a single string consisting of the elements of the iterable separated by the specified separator.

To join list elements with a specific separator, call.join() on the separator string. You then need to pass the list as an argument to combine the elements with the chosen separator. For example,"...".join(["ready", "set", "go"]) joins the three list elements"ready","set" and"go" with three dots ("...") in between them, returning the new string element"ready...set...go".

For simple concatenation of a few strings, you can use the concatenation operator (+) or string interpolation with f-strings. However,.join() is more efficient for combining many strings or an iterable with a variable amount of strings.

The string method.join() is designed so that the separator itself calls the method. You then pass the list—or another iterable of strings—as the argument. For example,",".join(items) tells Python that it should take all elements initems and join them using a comma. This may feel somewhat reversed compared to methods like.split(), but because it’s astring method, you need to call it on a single string object.

In this case, you’ll encounter aTypeError because.join() can only concatenate strings. You can avoid this by converting non-string elements to strings, like with[str(item) for item in my_list] ormap(str, my_list).

Yes! If you pass a string as the argument to.join(), then Python iterates over its characters. So"!".join("ABC") results in"A!B!C". This can be handy when you need to insert a separator between every character in a string.

Yes,.join() processes the iterable in the same order that it appears in your data structure. It doesn’t rearrange or sort the elements.

Take the Quiz: Test your knowledge with our interactive “How to Join Strings in Python” quiz. You’ll receive a score upon completion to help you track your learning progress:


How to Join Strings in Python

Interactive Quiz

How to Join Strings in Python

Test your understanding of Python's .join() string method for combining strings, handling edge cases, and optimizing performance.

🐍 Python Tricks 💌

Get a short & sweetPython Trick delivered to your inbox every couple of days. No spam ever. Unsubscribe any time. Curated by the Real Python team.

Python Tricks Dictionary Merge

AboutMartin Breuss

Martin is Real Python's Head of Content Strategy. With a background in education, he's worked as a coding mentor, code reviewer, curriculum developer, bootcamp instructor, and instructional designer.

» More about Martin

Each tutorial at Real Python is created by a team of developers so that it meets our high quality standards. The team members who worked on this tutorial are:

MasterReal-World Python Skills With Unlimited Access to Real Python

Locked learning resources

Join us and get access to thousands of tutorials, hands-on video courses, and a community of expert Pythonistas:

Level Up Your Python Skills »

MasterReal-World Python Skills
With Unlimited Access to Real Python

Locked learning resources

Join us and get access to thousands of tutorials, hands-on video courses, and a community of expert Pythonistas:

Level Up Your Python Skills »

What Do You Think?

Rate this article:

What’s your #1 takeaway or favorite thing you learned? How are you going to put your newfound skills to use? Leave a comment below and let us know.

Commenting Tips: The most useful comments are those written with the goal of learning from or helping out other students.Get tips for asking good questions andget answers to common questions in our support portal.


Looking for a real-time conversation? Visit theReal Python Community Chat or join the next“Office Hours” Live Q&A Session. Happy Pythoning!

Keep Learning

Related Topics:basicspython

Related Learning Paths:

Related Tutorials:

Keep reading Real Python by creating a free account or signing in:

Already have an account?Sign-In

Almost there! Complete this form and click the button below to gain instant access:

How to Join Strings in Python

How to Join Strings in Python (Sample Code)

🔒 No spam. We take your privacy seriously.


[8]ページ先頭

©2009-2026 Movatter.jp