In C++, how to print ASCII art to the console? - c++

Let's say you want to print out one of those great ASCII art images. How can you do that without cout each line individually?

Adjacent string literals are concatenated, so you can do this:
cout << " _______________________ _______ _ _______ _______ _______ _______ _ _______ \n"
"( ____ \__ __/ ___ ) ____ \ \ /\ ( ___ )\ /| ____ \ ____ )( ____ \ \ ( ___ )\ /|\n"
"| ( \/ ) ( | ( ) | ( \/ \ / / | ( ) | ) ( | ( \/ ( )|| ( \/ ( | ( ) | ) ( |\n"
"| (_____ | | | (___) | | | (_/ / | | | | | | | (__ | (____)|| (__ | | | | | | | _ | |\n"
"(_____ ) | | | ___ | | | _ ( | | | | ( ) ) __) | __)| __) | | | | | | |( )| |\n"
" ) | | | | ( ) | | | ( \ \ | | | |\ \_/ /| ( | (\ ( | ( | | | | | | || || |\n"
"/\____) | | | | ) ( | (____/\ / \ \ | (___) | \ / | (____/\ ) \ \__| ) | (____/\ (___) | () () |\n"
"\_______) )_( |/ \|_______/_/ \/ (_______) \_/ (_______// \__/|/ (_______/_______)_______)\n";
Or, more accurately, perhaps:
cout << " .::/- \n"
" .+++/ \n"
" `.::` /+++. \n"
" -////. :+++- \n"
" .////-` .+++/` \n"
" `:///:` `/++/. \n"
" ..` -////. -+++: \n"
" :+++:-` .////:` ./++/` \n"
" `-/+++++/-. `:////.`:++/. \n"
" `.:/++++/:.` -////..:--` \n"
" .-/+++++/-..::.` \n"
" `:::-..`` `.:/++++- \n"
" -++++++///:--.```.-/- \n"
" `.--:///++++++//::. \n"
"`--. ``..-::///+/``--- -+- ./oso- /++: \n"
"-oo+ -::::----....````... `ooo :s- /mo -dmmhy:`hmmo \n"
"-oo+ /+++++++++++++++++/. `ooo om: /mo ```` ``` ``` ``.`` ``` `.`` ommd`` `hmmo ``.`` ``` ``` ``` \n"
"-oo+ ...----::::////+++/` `ooo `/ssyss+:`.ohmyoo` .+ssyss+- -+syys+- /mo -o+. .ohdmmdho- -hdd/ `sdds` :shmmmdy/` .hddshdmmhoydmmmhy:`hmmo .+hdmmmds- .ddd/ .ddh- +ddh. \n"
"-oo+ ``````````````````` `ooo .yh-.``-/- .sm/.` `/o-```-sd+ .sd+-..-++` /mo .odo. :dmmy+/smmm: +mmh- /mmd- +mmh+:/smmy- .dmmdo/+s:`/ymmm++.`hmmo .dmmh++smmd+`ommd` `ymmmy .hmm+ \n"
"-oo+ +oooooooooooooooooo- `ooo -dy. om: -dy` +m/ /mo`+dy- `smmy` `smmy``smms`.hmm/ -dmd+---:hmmo`.dmm+ ommd `hmmo ommh. ommh..ymm+ +mmdmm/ ommy. \n"
"-oo+ /++++++++++++++++++. `ooo -oyhyyys/` om: `:osyyyyymy``sm- /myhyhd: `smms +mmh` `dmm/smms :dmmddddddddo`.dmm/ ommd `hmmo smmy` /mmd. :dmd+dmy-ymd+hmd: \n"
"-oo+ `ooo ``.+do om: /do. -dy``om: /md/``od+` `ommh. `ymmy` :dmmmmy. .hmd/`````.` .dmm/ ommd hmmo +mmh- smmy` `smmmmm- :dmmmmo \n"
"-oo+:::::::::::::::::::::::/ooo -+:.```.od+ +mo.` /do.```.omy` .sd/.``.//` /mo +dy. -ymmdysdmmh- +mmmh- :dmmyoosdd+` .dmm/ ommd ommmso.`ymmdyshmmh: .hmmm+ +mmmd` \n"
"-oooooooooooooooooooooooooooooo ./syyyyyo:` `:sys.`:syyyys+yo` `:syyyyo:` :h/ :ys` `:shddhs/` `ohy/ ./shddhy+- .shh: /hhy `:syhs. `:oyhdhs/. /hho` `shh/ \n"
More sensibly, use endl. This is subtly different from just "\n" after each line, because you'll also flush the output stream.

try something like:
cout << R"(place multiple lines
of text here
and it will display exactly
as you have it between the two brackets,
line feeds and all.)";
...the above code will also allow you to use characters like the backslash \ without needing two of them, it displays everything and doesn't recognize control codes, like \n etc. Very handy.
This is called a "string literal" and was added in C++11. You can find more information on the commands here, specifically refer to the prefix "R" which is for raw_characters: https://en.cppreference.com/w/cpp/language/string_literal

Others have already suggested using endl. While this isn't (necessarily) a bad thing, using endl flushes the stream's buffer along with writing a new-line. Contrary to the implication in one of the answers you've gotten, using endl does not help (at all) with translating the new-line to whatever character sequence the platform normally uses to signal the end of a line. Using newline is guaranteed to be precisely equivalent to stream << "\n" << flush;". Translating new-lines to "\r", or "\n" or "\r\n", or whatever the platform prefers, is done at a different level and newline has nothing to do with it.
The flush that it does, however, can (and often will) slow down your I/O, sometimes by quite a considerable margin. As long as you're only writing a few lines (e.g. a couple hundred characters) it's probably completely irrelevant. If you're writing a large file, however, using endl instead of "\n" can easily result in a 10x slowdown (in fact, I'd go so far as to say that much of the idea that iostreams are slow stems directly from using endl).
That's not to say there's never any reason to use endl. The flush assures that whatever has been written to the stream is immediately flushed out of the standard library's buffer, and sent to the OS. If you want to assure immediate display, endl can be useful. Likewise, if you're doing logging, and it's critical that your log always reflect the most recent known state of a program, endl can be (extremely) useful to assure that what you've written really gets logged, not lost in a buffer when/if the application crashes.
So, endl makes sense at times, but probably 95% of the time that it's used, it's really inappropriate (e.g., it's unlikely to accomplish anything useful in any of the answers to this question).

It's pretty simple thankfully. Just use endl whenever you want to start another line.
cout << stuff << endl
<< morestuff << endl
<< evenmorestuff << endl;
I would like to state that I much prefer using endl because it should work even if you are on a platform that requires "\r\n" instead of just "\n".

Related

How to replace multiple sub occurrences of string

I have one use case where I can have a text string which can contain anything. What I want to achieve is to replace a certain pattern within that given string.
Let's say I have given string as
:es1
es2
aaes1aa
:es3,
es1:
ees1,
ees1
{
"es1 :
What I am trying to do is here is suppose I have to replace all es1 in this string but with one condition. It has to be either end or start with [, | ; | : | " | ' | \\ | \s]. :es1, es1,, es1: and so on are accepted but eees1sss is not.
I tried ([, | ; | : | " | ' | \\ | \s])(es1)([, | ; | : | " | ' | , | \s]) something like this but I don't think it's what I need.
Go program:
match := regexp.MustCompile(`([, | ; | : | " | ' | \\ | \s])(es1)([, | ; | : | " | ' | , | \s])`)
test := `:es1
es2
aaes1aa
:es3,
es1:
ees1,
ees1
{
"es1 :`
fmt.Println(match.ReplaceAllString(test, "$1es4$3"))
output:
es2
aaes1aa
:es3,
:
ees1,
ees1
{
:
I was expecting my output to be more like
:es4
es2
aaes1aa
:es3,
es4:
ees1,
ees1
{
"es4 :
the solution provided below is not well tested against all possibilities, but it seems to be working.
package main
import (
"fmt"
"regexp"
)
func main() {
match := regexp.MustCompile(`([, | ; | : | " | ' | \\ | \s])es1|^es1([, | ; | : | " | ' | , | \s])`)
test := `:es1
es2
aaes1aa
:es3,
es1:
ees1,
ees1
{
"es1 :`
fmt.Println(match.ReplaceAllString(test, "${1}es4${2}"))
}
https://play.golang.org/p/E8lb9vmM_Sa
You can use
package main
import (
"fmt"
"regexp"
)
func main() {
match := regexp.MustCompile(`([,;:"'\\\s])es1\b|\bes1([,;:"'\\\s])`)
test := ":es1\n es2\n aaes1aa\n :es3,\n es1:\n ees1,\n ees1 \n \n {\n \"es1 :"
fmt.Println(match.ReplaceAllString(test, "${1}es4$2"))
}
See the Go demo and the regex demo. Note that the spaces and | chars inside square brackets are meaningful and match these chars literally, thus, you need to remove them all from your pattern.
The regex matches:
([,;:"'\\\s])es1\b - Group 1: a comma, or a semi-colon, colon, double or single quotation mark, backslash or whitespace; then es1 as a whole word (\b is a word boundary)
| - or
\bes1 - a whole word es1
([,;:"'\\\s]) - Group 2: a comma, or a semi-colon, colon, double or single quotation mark, backslash or whitespace

Multiple IF AND statements in one line with OpenOffice Calc

I'm using multiple IF AND statements in one cell and finding operator missing error 509. It worked with fewer variables just not sure the syntax is correct for calc here.
tried using nested statement with error 509 returned as well.
=IF(M5="Statement 1";L5;K5)IF(AND(M6="Tax";A5=A6); | L6;K6);IF(AND(M7="Discounts";A7=A6); | L7;K7);IF(AND(M8="Alternate";A8=A7); | L8;K8);IF(AND(M9="Other";A9=A8); | L9;K9);IF(AND(M10="Local";A10=A9); | L10;K10);IF(AND(M11="State";A11=A10); | L11;K11)
Desired outcome: Trying to get this output pending all values are true: L5 | L6 | L7 | L8 | L9 | L10 | L11
Current outcome: Error:509 which is Operator Missing error.
=IF(M5="Statement 1";L5;K5) missing& IF(AND(M6="Tax";A5=A6); missing & followed by quotes | missing quotes followed by & L6;K6) ; does not belong here should be &;IF(AND(M7="Discounts";A7=A6); | L7;K7);IF(AND(M8="Alternate";A8=A7); | L8;K8);IF(AND(M9="Other";A9=A8); | L9;K9);IF(AND(M10="Local";A10=A9); | L10;K10);IF(AND(M11="State";A11=A10); | L11;K11)
=if(M5="Statement 1";L5;K5)&if(AND(M6="Tax";A5=A6); "|" & L6;K6)&if(AND(M7="Discounts";A7=A6); "|" & L7;K7)&if(AND(M8="Alternate";A8=A7); "|" & L8;K8)&if(AND(M9="Other";A9=A8); "|" & L9;K9)&if(AND(M10="Local";A10=A9); "|" & L10;K10)&if(AND(M11="State";A11=A10); "|" & L11;K11)

Only Detect Text in Quotations (C++)

I'm not great at programming and recently started to read tutorials on C++.
I decided I would attempt to make a simple blackjack program. I tried to make a title with "big text" but C++ is preventing me from doing it because it is detecting other things inside the text.
//Start Screen Begin
cout << " ____ _ _ _ _ ";
cout << "| __ )| | __ _ ___| | __(_) __ _ ___| | __ ";
cout << "| _ \| |/ _` |/ __| |/ /| |/ _` |/ __| |/ / ";
cout << "| |_) | | (_| | (__| < | | (_| | (__| < ";
cout << "|____/|_|\__,_|\___|_|\_\/ |\__,_|\___|_|\_\ ";
cout << " |__/ ";
//Start Screen End
This is what I am trying to display, yet keep getting the following error:
undefined reference to 'WinMain#16'
I am asking if there is a way to tell C++ I only want it to read and display the text, and not use any functions.
That's a better job for C++11 raw string literals than escaping \ with \\:
#include <iostream>
int main() {
using namespace std;
//Start Screen Begin
cout << R"( ____ _ _ _ _ )" << '\n';
cout << R"(| __ )| | __ _ ___| | __(_) __ _ ___| | __ )" << '\n';
cout << R"(| _ \| |/ _` |/ __| |/ /| |/ _` |/ __| |/ / )" << '\n';
cout << R"(| |_) | | (_| | (__| < | | (_| | (__| < )" << '\n';
cout << R"(|____/|_|\__,_|\___|_|\_\/ |\__,_|\___|_|\_\ )" << '\n';
cout << R"( |__/ )" << '\n';
//Start Screen End
}
Check the output here that it works for a decent compiler that support C++11: http://coliru.stacked-crooked.com/a/964b0d2b8bde8b3d
The following would also work:
#include <iostream>
int main() {
using namespace std;
//Start Screen Begin
cout <<
R"(
____ _ _ _ _
| __ )| | __ _ ___| | __(_) __ _ ___| | __
| _ \| |/ _` |/ __| |/ /| |/ _` |/ __| |/ /
| |_) | | (_| | (__| < | | (_| | (__| <
|____/|_|\__,_|\___|_|\_\/ |\__,_|\___|_|\_\
|__/
)";
//Start Screen End
}
http://coliru.stacked-crooked.com/a/b89a0461ab8cdc97
Your second-to-last text literal has several \ characters in it. That is an escape character, so to use the literal \ character you have to escape it as \\, eg:
cout << "|____/|_|\\__,_|\\___|_|\\_\\/ |\\__,_|\\___|_|\\_\\ ";
It won't look as good in code, but it will look fine when the app is run.
As for the reference error, WinMain() is the entry point for GUI apps, whereas main() is the entry point for console apps, so it sounds like you did not create/configure your project correctly if it is trying to link to WinMain() instead of main().
You'll need to escape the backslashes, instead of one \ have two \\.
These are used to indicate special characters like "\n" (line-break) appearing within a string literal ("..."). Your Big-Text misses all of those line-breaks BTW.
undefined reference to 'WinMain#16'
Apparently you are trying to compile a GUI project. Check your Code Blocks project type.

code optimization

I must write a function "to_string" wich receives this datatype
datatype prop = Atom of string | Not of prop | And of prop*prop | Or of prop*prop;
and returns a string.
Example
show
And(Atom("saturday"),Atom("night")) =
"(saturday & night)"
My function is working but I have 2 problems.
the interpreter tells me -> Warning: match nonexhaustive
I think i can write the function with locals functions for all the types (Not, And, Or) and avoid duplicate code but I don't know how.
there is my code
datatype prop = Atom of string | Not of prop | And of prop*prop | Or of prop*prop;
fun show(Atom(alpha)) = alpha
| show(Not(Atom(alpha))) = "(- "^alpha^" )"
| show(Or(Atom(alpha),Atom(beta))) = "( "^alpha^" | "^beta^" )"
| show(Not(Or(Atom(alpha),Atom(beta)))) = "(- ( "^alpha^" | "^beta^" ))"
| show(Or(Not(Atom(alpha)),Atom(beta))) = "( (-"^alpha^") | "^beta^" )"
| show(Or(Atom(alpha),Not(Atom(beta)))) = "( "^alpha^" | (-"^beta^") )"
| show(Or(Not(Atom(alpha)),Not(Atom(beta)))) = "( (-"^alpha^") | (-"^beta^") )"
| show(And(Atom(alpha),Atom(beta))) = "( "^alpha^" & "^beta^" )"
| show(Not(And(Atom(alpha),Atom(beta)))) = "(- ( "^alpha^" & "^beta^" ))"
| show(And(Not(Atom(alpha)),Atom(beta))) = "( (-"^alpha^") & "^beta^" )"
| show(And(Atom(alpha),Not(Atom(beta)))) = "( "^alpha^" & (-"^beta^") )"
| show(And(Not(Atom(alpha)),Not(Atom(beta)))) = "( (-"^alpha^") & (-"^beta^") )";
Thanks a lot for your help.
The general rule is as follows: if you have a recursive data type, you should use a recursive function to transform it.
Your match expression is not exhaustive because there are a lot of variants you can't handle - i.e. And(And(Atom("a"), Atom("b")), Atom("c")).
You should rewrite the function with recursive calls to itself - i.e. replace Not(Atom(alpha)) match with Not(expr):
show(Not(expr)) = "(- " ^ show(expr) ^ " )"
I'm sure you can figure out the rest (you'll have two recursive calls for and/or).

Regular Expression Period Issue

((https?|ftp)://|www.)(\S+[^.*])
I would like this expression to check for . in succession to each other. If it finds two or more periods back to back, the expression should fail. On the other hand, if it succeeds, I want it to match every character and/or symbol up until the first white space encountered.
In other words:
www.yahoo..com should fail
On a related note: I realize that this expression is very basic in terms of judging valid URL structure. I have another "more intelligent" regular expression in place that precedes the one above. The purpose of the posted one is meant to check the validity of the URL that is passed from the initial regular expression via preg_match_all.
You may awnt to check out FILTER_VALIDATE_URL with http://php.net/manual/en/book.filter.php instead of using Regex to validate your URLS.
Here's example usage:
$url = "http://www.example.com";
if(!filter_var($url, FILTER_VALIDATE_URL))
{
echo "URL is not valid";
}
else
{
echo "URL is valid";
}
You can do something like this:
((https?|ftp)\:\/\/|www.)((?:[\w\-]+\.)*[\w\-]+)
This will not yet check for valid URLs, even if you skip double dots. I'd advise not to use regex if the language you're using (PHP?) has other means of validating an URL.
The RFC states the following:
; URL schemeparts for ip based protocols:
ip-schemepart = "//" login [ "/" urlpath ]
login = [ user [ ":" password ] "#" ] hostport
hostport = host [ ":" port ]
host = hostname | hostnumber
hostname = *[ domainlabel "." ] toplabel
domainlabel = alphadigit | alphadigit *[ alphadigit | "-" ] alphadigit
toplabel = alpha | alpha *[ alphadigit | "-" ] alphadigit
alphadigit = alpha | digit
hostnumber = digits "." digits "." digits "." digits
port = digits
user = *[ uchar | ";" | "?" | "&" | "=" ]
password = *[ uchar | ";" | "?" | "&" | "=" ]
urlpath = *xchar ; depends on protocol see section 3.1
; HTTP
httpurl = "http://" hostport [ "/" hpath [ "?" search ]]
hpath = hsegment *[ "/" hsegment ]
hsegment = *[ uchar | ";" | ":" | "#" | "&" | "=" ]
search = *[ uchar | ";" | ":" | "#" | "&" | "=" ]
; Miscellaneous definitions
lowalpha = "a" | "b" | "c" | "d" | "e" | "f" | "g" | "h" |
"i" | "j" | "k" | "l" | "m" | "n" | "o" | "p" |
"q" | "r" | "s" | "t" | "u" | "v" | "w" | "x" |
"y" | "z"
hialpha = "A" | "B" | "C" | "D" | "E" | "F" | "G" | "H" | "I" |
"J" | "K" | "L" | "M" | "N" | "O" | "P" | "Q" | "R" |
"S" | "T" | "U" | "V" | "W" | "X" | "Y" | "Z"
alpha = lowalpha | hialpha
digit = "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" |
"8" | "9"
safe = "$" | "-" | "_" | "." | "+"
extra = "!" | "*" | "'" | "(" | ")" | ","
national = "{" | "}" | "|" | "\" | "^" | "~" | "[" | "]" | "`"
punctuation = "<" | ">" | "#" | "%" | <">
reserved = ";" | "/" | "?" | ":" | "#" | "&" | "="
hex = digit | "A" | "B" | "C" | "D" | "E" | "F" |
"a" | "b" | "c" | "d" | "e" | "f"
escape = "%" hex hex
unreserved = alpha | digit | safe | extra
uchar = unreserved | escape
xchar = unreserved | reserved | escape
digits = 1*digit
Using negative lookahead is an easy way if your engine supports it:
(?!.*\.\.)((https?|ftp)\:\/\/|www.)(\S+[^.*])
Otherwise, you have to be more specific:
^((https?|ftp)\:\/\/|www.)((\.[^.]|[^.\s])+[^.*])($|\s+)