avatarCarolyn Hastings

Free AI web copilot to create summaries, insights and extended knowledge, download it at here

6469

Abstract

market dynamics. This is where feature engineering becomes invaluable. By transforming and synthesizing the raw data using established technical indicators, we can provide the model with enriched insights that could explain underlying market patterns and trends. Such enriched data can significantly improve the model’s ability to anticipate future price movements.</p><p id="07ea">For this forecast, we will utilize a couple of technical indicators for our feature engineering like RSI, MACD, Bollinger Bands, Parabolic SAR, and Stochastic Oscillator. Additionally, we introduce lag features to capture temporal dependencies, ensuring our model benefits from both current and historical contexts.</p><p id="f61d"><b>Let’s calculate the features we will utilize in this forecast</b></p><div id="d4ed"><pre><span class="hljs-comment"># Compute RSI</span> df[<span class="hljs-string">'momentum_rsi'</span>] = RSIIndicator(close=df[<span class="hljs-string">'Close'</span>]).rsi()

<span class="hljs-comment"># Compute MACD</span> macd = MACD(close=df[<span class="hljs-string">'Close'</span>]) df[<span class="hljs-string">'trend_macd'</span>] = macd.macd() df[<span class="hljs-string">'trend_macd_signal'</span>] = macd.macd_signal() df[<span class="hljs-string">'trend_macd_diff'</span>] = macd.macd_diff()

<span class="hljs-comment"># Compute Bollinger Bands</span> bollinger = BollingerBands(close=df[<span class="hljs-string">'Close'</span>]) df[<span class="hljs-string">'volatility_bbm'</span>] = bollinger.bollinger_mavg() df[<span class="hljs-string">'volatility_bbl'</span>] = bollinger.bollinger_lband() df[<span class="hljs-string">'volatility_bbh'</span>] = bollinger.bollinger_hband()

<span class="hljs-comment"># Compute Parabolic SAR</span> psar = PSARIndicator(high=df[<span class="hljs-string">'High'</span>], low=df[<span class="hljs-string">'Low'</span>], close=df[<span class="hljs-string">'Close'</span>]) <span class="hljs-comment"># Assuming you have 'High' and 'Low' columns in your df</span> df[<span class="hljs-string">'trend_psar'</span>] = psar.psar()

<span class="hljs-comment"># Compute Stochastic Oscillator</span> stochastic = StochasticOscillator(high=df[<span class="hljs-string">'High'</span>], low=df[<span class="hljs-string">'Low'</span>], close=df[<span class="hljs-string">'Close'</span>]) <span class="hljs-comment"># Assuming you have 'High' and 'Low' columns</span> df[<span class="hljs-string">'momentum_stoch'</span>] = stochastic.stoch() df[<span class="hljs-string">'momentum_stoch_signal'</span>] = stochastic.stoch_signal()

<span class="hljs-comment"># Create Lag Features</span> df[<span class="hljs-string">'Close_Lag1'</span>] = df[<span class="hljs-string">'Close'</span>].shift(<span class="hljs-number">1</span>)

<span class="hljs-comment"># Drop NaN values introduced due to lag features and indicators</span> df = df.dropna()

<span class="hljs-comment"># Define features and target</span> X = df[[<span class="hljs-string">'momentum_rsi'</span>, <span class="hljs-string">'trend_macd'</span>, <span class="hljs-string">'trend_macd_signal'</span>, <span class="hljs-string">'trend_macd_diff'</span>, <span class="hljs-string">'volatility_bbm'</span>, <span class="hljs-string">'volatility_bbl'</span>, <span class="hljs-string">'volatility_bbh'</span>, <span class="hljs-string">'trend_psar'</span>, <span class="hljs-string">'momentum_stoch'</span>, <span class="hljs-string">'momentum_stoch_signal'</span>, <span class="hljs-string">'Close_Lag1'</span>]] y = df[<span class="hljs-string">'Close'</span>]</pre></div><p id="712f">The above code is organizing the dataset <code>df</code> into input features and a target variable for our model. The input features, captured under <code>X</code>, consist of various the features we calculated on and previously defined. The target variable, denoted by <code>y</code>, is the <code>Close</code> column, representing the daily closing price of EUR/USD, which our model aims to predict based on the provided features.</p><p id="bdfb"><b>Model Initialization and Training</b></p><div id="a7d2"><pre><span class="hljs-comment"># Initialize the model</span> model = xgb.XGBRegressor( learning_rate=<span class="hljs-number">0.75</span>, n_estimators=<span class="hljs-number">200</span>, max_depth=<span class="hljs-number">5</span>, subsample=<span class="hljs-number">0.9</span>, colsample_bytree=<span class="hljs-number">0.8</span>, colsample_bylevel=<span class="hljs-number">0.8</span>, gamma=<span class="hljs-number">0</span>, min_child_weight=<span class="hljs-number">1</span> )

<span class="hljs-comment"># Train the model</span> model.fit(X_train, y_train)</pre></div><p id="7ce9">Continuing from the previously discussed data preparation, this section of code dives into the model initialization and training phases using XGBoost. The <code>xgb.XGBRegressor()</code> initializes a regression model with specified hyperparameters to optimize the forecast. Key parameters include a learning rate of <code>0.75</code>, which determines the step size at each iteration while optimizing, <code>200</code> estimators or trees, and a maximum depth of <code>5</code> for each tree, among others. These hyperparameters play a role in controlling the model’s complexity and fit to the data.</p><p id="4e91">After initializing, the model is trained on the <code>X_train</code> and <code>y_train</code> datasets using the <code>fit</code> method. This step allows the model to learn the underlying patterns from the training data, preparing it to make future predictions on unseen data.</p><p id="95cf"><b>Performance Evaluation and Testing</b></p><div id="a823"><pre><span class="hljs-comment"># Predict on the test set</span> y_pred = model.predict(X_test)

<span class="hljs-comment"># Calculate performance metrics</span> mae = mean_absolute_error(y_test, y_pred) mse = mean_squared_error(y_test, y_pred) rmse = np.sqrt(mse)

<span class="hljs-built_in">print</span>(<span class="hljs-string">f"Mean Absolute Error: <span class="hljs-subst">{mae}</span>"</span>) <span class="hljs-built_in">print</span>(<span class="hljs-string">f"Mean Squared Error: <span class="hljs-subst">{mse}</span>"</span>) <span class="hljs-built_in">print</span>(<span class="hljs-string">f"Root Mean Squared Error: <span class="hljs-subst">{rmse}</span>"</span>)

y_train_pred = model.predict(X_train)</pre></div><p id="8c56">After training the

Options

model on the historical data we evaluate its performance on unseen or test data. Using the <code>predict</code> method of the trained model, predictions (<code>y_pred</code>) are generated for the test dataset <code>X_test</code>. Subsequently, to assess the accuracy and reliability of these predictions, various performance metrics are computed:</p><ul><li><b>The Mean Absolute Error (MAE)</b> provides an average magnitude of errors between predicted and actual values.</li><li><b>The Mean Squared Error (MSE) </b>squares these errors to emphasize larger discrepancies.</li><li><b>Root Mean Squared Error (RMSE) </b>is the square root of MSE, providing error in the same units as the original data.</li></ul><p id="c92b">These metrics are then printed for clear visibility. We concludes by also predicting on the training set (<code>X_train</code>) with <code>y_train_pred</code>, to further analyze and compare the model’s performance on both training and test datasets.</p><p id="44c0">The following output displays the performance metricswhich assess the accuracy of our model’s predictions:</p><div id="6743"><pre><span class="hljs-attribute">Mean</span> Absolute Error: <span class="hljs-number">0</span>.<span class="hljs-number">009141215039947168</span> <span class="hljs-attribute">Mean</span> Squared Error: <span class="hljs-number">0</span>.<span class="hljs-number">000303615460154008</span> <span class="hljs-attribute">Root</span> Mean Squared Error: <span class="hljs-number">0</span>.<span class="hljs-number">017424564848340058</span></pre></div><ul><li><b>Mean Absolute Error (MAE): </b>At 0.0091, it shows the model’s average absolute deviation from the actual values.</li><li><b>Mean Squared Error (MSE):</b> With a value of 0.0003036, it indicates the average squared error, emphasizing larger mistakes.</li><li><b>Root Mean Squared Error (RMSE):</b> At 0.0174, it provides the average error in the original unit, illustrating the typical magnitude of error.</li></ul><p id="7500">The relatively low values across these metrics suggest that the model has a good degree of accuracy in its predictions. The model appears to be reliably forecasting the target variable, depicted with minimal deviations in the forecasted data when compared to the actual data.</p><p id="be3b"><b>Data Visualization</b></p><div id="2b49"><pre><span class="hljs-comment"># Create a new DataFrame for visualization</span> viz_df = pd.DataFrame({<span class="hljs-string">'True'</span>: y_test, <span class="hljs-string">'Predicted'</span>: y_pred})

<span class="hljs-comment"># Concatenate the training data for a complete view</span> viz_df_train = pd.DataFrame({<span class="hljs-string">'True'</span>: y_train, <span class="hljs-string">'Predicted'</span>: y_train_pred}) viz_df = pd.concat([viz_df_train, viz_df])

<span class="hljs-comment"># Plot the results</span> plt.figure(figsize=(<span class="hljs-number">14</span>, <span class="hljs-number">7</span>)) plt.plot(viz_df[<span class="hljs-string">'True'</span>], label=<span class="hljs-string">'True'</span>, color=<span class="hljs-string">'blue'</span>) plt.plot(viz_df[<span class="hljs-string">'Predicted'</span>], label=<span class="hljs-string">'Predicted'</span>, color=<span class="hljs-string">'red'</span>, alpha=<span class="hljs-number">0.7</span>) plt.title(<span class="hljs-string">'EUR/USD Forecast: True vs Predicted'</span>) plt.legend() plt.grid(<span class="hljs-literal">True</span>) plt.show()</pre></div><figure id="ce5c"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*cLlTTCFRMZqUBQIUBeya0g.png"><figcaption></figcaption></figure><p id="62e5">The visual representation of the EUR/USD currency pair’s forecasted versus actual values offers an insightful glimpse into the model’s capabilities. The close alignment between the blue <code>True</code> line and the red <code>Predicted</code> line for most of the chart affirms the model’s strong predictive proficiency, especially given the low Mean Absolute Error (MAE) of 0.0091. The few areas where deviations occur resonate with the Root Mean Squared Error (RMSE) of 0.0174, indicating the average magnitude of error.</p><p id="ba85">Notably, the small segment towards the right end, where predictions seem to diverge slightly, underscores the challenges of exact currency forecasting. Nevertheless, the model, as depicted in the graph and corroborated by the performance metrics, has shown remarkable accuracy in capturing the nuances of the EUR/USD exchange rate’s movements.</p><h1 id="fe27">Conclusion</h1><p id="3036">In conclusion, this exploration into Forex forecasting has underscored the critical interplay between data preprocessing, feature engineering, and model selection. Through this model we found that XGBoost in predicting the EUR/USD currency pair stands out, demonstrating the algorithm’s robustness and adaptability. Finally, the precision showcased by our model reinforces XGBoost’s reputation as an efficient tool to forecast financial data.</p><p id="0141">Read more of my stories here:</p><div id="c60c" class="link-block"> <a href="https://algocraft.xyz/eur-usd-forecasting-simplified-an-lstm-users-guide-337ccdda6158"> <div> <div> <h2>EUR/USD Forecasting Simplified: an LSTM User’s Guide</h2> <div><h3>LSTM, or Long Short-Term Memory, is a specialized type of Recurrent Neural Network (RNN) designed to recognize patterns…</h3></div> <div><p>algocraft.xyz</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/1*EUIE-cUkt3x2AqBX5nUotA.jpeg)"></div> </div> </div> </a> </div><div id="a6a6" class="link-block"> <a href="https://algocraft.xyz/how-to-get-131-return-with-mean-reversion-trading-strategy-from-stock-selection-to-backtesting-c623870adf31"> <div> <div> <h2>How to Get a 131% Return with Mean Reversion Trading Strategy: From Stock Selection to Backtesting</h2> <div><h3>undefined</h3></div> <div><p>undefined</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/0*o95y-D4ETf1Geqx3)"></div> </div> </div> </a> </div></article></body>

AI Poetry | Twittles

How Twittle and I Outsmarted ChatGPT!

Putting ChatGPT to the twittle test

Image by Mohamed Hassan from Pixabay — recoloured by author in Pixlr

ChatGPT is a content disruptor a tossed spanner in the works Do we shrug and say ‘whatever’ or teach ourselves re: its quirks?

No doubt you’ve heard about ChatGPT, Open AI’s chatbot that has been causing a global hooha.

It doesn’t matter which side of the content creation fence you’re on — creator or consumer — ChatGPT, and other AI chatbots, are wheedling their way into our lives.

And they’ll continue to do that for as long as we have networks of computers interacting with each other i.e. the internet.

As content creators on an open, online writing platform like Medium, we’re in charge of our own writing. We can choose to make use of AI tools like ChatGPT if we like but with it comes an obligation to do so responsibly and with integrity. That, I’m pleased to see, appears to be the stand Medium is taking on the matter.

As a follow-on to his post, What do you think about AI-generated writing?, Scott Lamb, Medium’s content VP, reported in a recent mail out of The Edition (subject line: Surprisingly creative uses for AI), ‘We’re still working through our approach to such content and will have more to share soon, but are leaning towards transparency and disclosure as necessary first steps.’

While we ‘watch this space’ for further announcements from Medium, I decided to be proactive and put ChatGPT through some hoops of my own. I was curious to see how it performed. But more than that, I needed to know if I’ve outsmarted it with twittles!

I’m here to tell you I have! 😊

…for now! 🙄

Outsmarting ChatGPT

Some of you will know already that I have a vested interest here in Medium — one I’ve been working on for over two years. It’s called twittle. The four-line rhyming micropoem you see at the top of this story is an example of a twittle.

Here’s another one -

I put ChatGPT to the twittle test. It spat out poems like it had the trots I laughed out loud, hee hee! at its untwittled poetry!

What makes twittles different to any other four-line rhyming verse?

That’s a question you can ask any twittler whose twittle has made it into the Twittle Treasury (the twittle list I curate here on Medium) and their answer will be the same: ‘100 alphabet letters’.

That’s it! How hard is that?

Well, too hard for ChatGPT it seems! 😆

It couldn’t get it right no matter how I worded the instruction.

Here, I’ll show you in this series of screenshots how ChatGPT responded to my instructions. Note: I’ve chosen not to reproduce ChatGPT’s poetry attempts in the body of this story because they’re not my words and would only serve to artificially inflate this story’s stats. I’ve also elected to limit my comments to the structural aspects of ChatGPT’s responses and how they relate to twittles — I’ll leave it to you to decide what you think of its aptitude for poetry.

Test 1: Write a twittle poem about love

screenshot by author

Outcome: ChatGPT responded with a 10-line poem comprising two quatrains and a couplet. We’ll ignore the couplet and focus on the quatrains since they’re in the form of a twittle. A quick check with the character count tool (see the screenshot below) shows the first quatrain is 127 letters and the second is 109 i.e. neither one is a twittle.

screenshot by author — stanza letter-count subtotals added in by author — total = 308

Comment: It would seem ChatGPT ignored the word ‘twittle’ in the instruction and wrote a poem about love. Is this an example of the chatbot not knowing what it doesn’t know or is it, as others have suggested, being ‘overconfident’ in thinking it knows more than it does?

It did not surprise me that ChatGPT might not have known the word ‘twittle’. I’m the one who coined the term in October 2020 and since then it’s been circulating around Medium and Twitter and to a lesser extent, Facebook.

If someone were to publish ChatGPT’s love poem on Medium and call it twittle poetry, sooner or later they would have me dropping them a PN telling them, as politely as I could, ‘Sorry, but your poem’s not a twittle’! 😜

If the poem were published elsewhere on the internet or in a book and labeled a twittle, it would be misrepresenting the twittle form and creating confusion among readers. That, for me, is a concern. 😟

To test my ‘ChatGPT-doesn’t-know-what-twittle-means’ hypothesis, I presented it with the next task.

Test 2: Write a twittle about flowers

screenshot by author

Outcome: ChatGPT responded with a poem constructed with three quatrain verses. I won’t bog you down with a screenshot of the character count (you can take my word for it, or count the letters yourself if you don’t trust me!) but the letter count per stanza is 98, 114, 125 i.e. none of them are twittles!

Comment: Even though I removed ‘poem’ from the instruction, ChatGPT still responded with a poem. In fact it responded in twittle-like quatrains which kinda disproved my hypothesis. 🙄

Maybe, ChatGPT knows more about twittles than I give it credit for. 🤔

What it’s not doing is meeting twittle’s 100-letter count requirement.

Test 3: Write a quatrain with 100 alphabet letters about grief

screenshot by author

Outcome: ChatGPT gave me a poem with not one but two quatrain verses, neither one of which has 100 letters! (129 and 120 letters respectively)

Comment: Thinking like a chatbot, I can see how it would have thought my instruction was ridiculous. I can hear it now: ‘Too easy! I don’t need 100 letters. I can do it in under 26 — assuming we’re talking English alphabet, that is!’

Smartypants! 😆

Aside from that, I have to question ChatGPT’s working definition for ‘quatrain’. In its basic form, a quatrain is a four-line rhyming verse, however it may also refer to a poem of any length constructed with quatrain stanzas.

Since ChatGPT gave me two in-series quatrains about grief, I have to assume it’s working from the latter definition i.e. a poem of quatrains.

Either that, or it didn’t pick up on the indefinite article ‘a’ in my instruction or the absence of a pluralising ‘s’ on ‘quatrain’. Surely, it knows Grammar 101? 🙄

ChatGPT’s developers suggest tweaking the instruction if it’s not giving you the responses you expect.

Ok, next test…

Test 4: Write a 100-letter quatrain about hope

screenshot by author

Outcome: ChatGPT tapped out another double quatrain poem with an excess of letters per stanza — 119, 131.

Comment: Tweaking the instruction made no difference to the outcome — same ol’ same ol’!

ChatGPT reminds me of a kid who only takes in half of what the teacher says and goes off and does their own thing! Like the kid’s teacher, it’s testing my patience! 😒

I have one more trick up my sleeve. 🙋‍♀️

Elsewhere in poetryville, twittles are known as dribbles (dreadful name, hence why I rebranded them).

Let’s see if ChatGPT can dribble! 😜

Test 5: Write a dribble poem about freedom

screenshot by author

Outcome: ChatGPT spewed out three quatrains none of which are dribbles aka twittles — letter counts: 112, 102, 118.

Comment: I give up! 🤷

Except I don’t. 😅

This exercise has proven ChatGPT can’t be trusted when it comes to a poetry form as specific as twittles.

Furthermore, it gives me hope that any twittles I come across (even the NQR ones) are more likely to have been written by a human than a bot.

Even if the poetry were AI-written, a human has tweaked it into shape — like I’m about to do with the second stanza of ChatGPT’s freedom poem. It really isn’t that hard to fix a twittle! 😉

It’s the right to speak, to choose, to be To live the lives we wish to see It’s the ability to fly, to soar Unshackled, forevermore

(I changed line 2 and corrected ‘forever more’ — erh, it’s one word, Chat!)

Punchline

I could have kept tweaking the instructions or started a new conversation to clear the history but I decided to pull the plug on my experiment and declare myself the winner!

YAY!! I know more about twittles than ChatGPT does!

👉 I can write twittles like this one 👇 and ChatGPT can’t! 👈

The world is abuzz about ChatGPT Open AI’s nifty-natty chatbot Friend or foe we can’t decide A twittler? — most definitely not!

I know it’s only a matter of time before ChatGPT gets its binaries around twittles but lucky for us we have a fabulous collection of authentic twittles written by our equally fabulous band of twittlers here on Medium. 😊 You can find them all in the Twittle Treasury

Jump on board the Twittle Expressery!

There’s always room for more twittlers on board the Twittle Expressery, stopping all stations around Medium. Take a look at who’s already on the twittle train —

Ann Marie Steele | Annie Trevaskis | Aza Y. Alam | Bear Kosik | Brandon Ellrich | Caroline de Braganza | Christina M. Ward | David Rudder | Denise Darby | Denise Estey Lindquist | Denise Kendig | Dennett | Diana Pippin | Era Garg | Evelyn Jean Pine | Gustave Deresse; Writer & AI Artist | Heather Lee | James G Brennan | James Scannell | Jaylee Reign | Jeff Langley | Jenine "Jeni" Bsharah Baines | Jesse Wilson | Jim McAulay🍁 | Joe Merkle | John Hansen | Julie Greenidge | K. Barrett | Kelly Aluna Martone | Kimberly Hampton Nilsson | Krystal | Lee Ameka | Lee David Tyrrell | Lu Skerdoo | Marilyn J Wolf | Megan Nicole Morgan | Melanie J. | Mia Verita | Misbah Sheikh | Monoreena Acharjee Majumdar | Nikolaos Skordilis | Orla K. | Patrick Eades | Patrick M. Ohana | Dr. Preeti Singh | Raine Lore | R. Rangan PhD | Samantha Lazar | Selma | Sheila McCall | Shereen Bingham | Sinus Kosinus | Susan Alison | Susannah MacKinnie | Ted Czukor | Tejaswini Nalubala | Thalia Dunn | TzeLin Sam | Venu | Will Hull | William J Spirdione

Want to learn more about twittles? Start here —

Thank you, Rui Alves, APEX, Margie Pearl at Engage for finding a place in your publication for my twittle vs AI story. 🙏 Maybe one day soon you’ll join us on the Twittle Expressery — just saying! 😉 💞

Thank you everyone for reading. 🙏 💕

© Carolyn Hastings 2023

✨ If you like what you’ve read, please consider — 👉 Subscribing to my email list 📩 👉 Becoming a Medium member using my affiliate referral link

ChatGPT
Twittle
Poetry
Writing On Medium
Engage
Recommended from ReadMedium
avatarPablo Pereyra
Dust And Light

A Poem

1 min read