SDC

  • Menü
    • Teknik Analiz
    • BorsaPin
    • Bitmeyen Senfoni
    • Halet-i Ruhiye
    • Anlık Tepkiler
    • Teknoloji
    • Karma Karışık
  • Hakkında
  • İletişim
  • BorsaPin
  • Home
  • Menü
    • Teknik Analiz
    • BorsaPin
    • Bitmeyen Senfoni
    • Halet-i Ruhiye
    • Anlık Tepkiler
    • Teknoloji
    • Karma Karışık
  • Hakkında
  • İletişim
  • BorsaPin

Ekrandaki Milyonluk Hacimler Gerçek mi, Yoksa Kurgu mu?

29 Ekim 2026 Borsa

Borsa ekranını açtığınızda bazen öyle bir tablo görürsünüz ki insanın aklı karışır: Bir hissede yüz milyonlarca lotluk işlem dönmüş, bilindik bazı aracı kurumlar tahtayı süpürmüş gibi duruyor. Telegram gruplarında veya Twitter’da hemen aynı fısıltı yayılır: “Falanca kurum malı topladı, bu tahta yakında roket!”

Peki piyasada herkesin diline pelesenk olan o meşhur mal toplama (akümülasyon)
Mal dağıtma ve yeniden toplama senaryosu gerçekten ekrandan iki tıkla anlaşılabilecek kadar basit mi?
Yoksa o devasa hacim rakamları çoğu zaman gözümüzü boyayan bir illüzyondan mı ibaret?

Gelin bu işin mutfağına inelim, rakamlarla ve piyasanın çıplak gerçekleriyle tane tane konuşalım.

1. Dolaşımdaki Lot Yanılgısı:

“Mal Toplandı” Demek Bu Kadar Kolay mı? Hemen kafamızda canlandıralım: Bir şirket düşünün, toplam sermayesi 1 milyar lot ve hisse fiyatı 8 TL olsun. Yani şirketin piyasa değeri 8 milyar TL.

Bu hisselerin 750 milyon lotu şirketin patronunda, kurucularında ya da uzun vadeli ana ortaklarda kilitli dursun; satmaya da hiç niyetleri olmasın. Geriye piyasada dönüp dolaşabilecek 250 milyon lot (yani %25 fiili dolaşım) kalır.

Bir gün baktınız, bir aracı kurum üzerinden 8 TL ortalamayla tam 100 milyon lotluk alım yapıldı. Parasal karşılığı tam 800 milyon TL. İlk bakışta düz mantık devreye girer: “250 milyonun 100 milyonunu çektiler, geriye kaldı 150 milyon lot. Tahtada mal azaldı, fiyat mecburen uçacak.”
Ama kazın ayağı her zaman öyle olmuyor.
Çünkü tahtada gerçekleşen her alım, o lotların kasaya kilitlendiği anlamına gelmez. Satın alınan paylar gün içinde ya da ertesi seans yeniden piyasaya salınabilir. Daha da önemlisi, tek bir kurum üzerinden geçen 100 milyon lotun tek bir kişiye mi, yoksa o kurumu kullanan yüzlerce farklı küçük yatırımcıya mı ait olduğunu sadece o anki aracı kurum dağılımına bakarak asla anlayamazsınız.

Burada sormamız gereken ilk soru şudur: Ne kadar mal alındığı değil, o malın gün sonunda gerçekten aynı ellerde kalıp kalmadığı.

2. Hacim Neden Kandırabilir? 

Diyelim ki hisse 8 TL seviyesindeyken tahtada 100 milyon lotluk işlem hacmi oluştu. Yani ekranda 800 milyon TL’lik bir trafik aktı.

Çoğu yatırımcı bunu “Piyasaya 800 milyon TL taze para girdi” şeklinde okur. Oysa borsada her alışın karşısında mutlaka bir satış vardır.

Şöyle düşünün: Elinizde 10 milyon lot var. Siz bu malı gün içinde algoritmalarla veya gün içi işlemlerle farklı hesaplar arasında 10 kere alıp satsanız, günün sonunda tahtada 100 milyon lotluk devasa bir hacim üretmiş olursunuz.

Ama gün bittiğinde elinizdeki lot sayısı yine aynıdır; piyasaya tek bir kuruş yeni para girmemiştir, tek bir lot bile kalıcı olarak toplanmamıştır.

İşte bu yüzden işlem hacmi ile takası birbirinden ayırmak şart:

Hacim: Gün içindeki trafiği, yani kuru gürültüyü gösterir.
Takas: Seans bittikten (T+2 takas takviminden) sonra o lotların kimin saklama hesabında gerçekten beklemeye geçtiğini gösterir.

Borsada hacim sadece bir vitrindir; asıl hikaye depoda, yani takasta yatar.

3. Fiyat Tırmanırken Mal Nasıl Usulca Dağıtılır?

Şimdi hikayeyi bir adım ileriye taşıyalım.

Hisse 8 TL’den 16 TL’ye soluksuz bir ralli yapmış olsun (%100 prim). 8 TL ortalamayla 100 milyon lotu alan o varsayımsal oyuncunun elindeki portföy 800 milyon TL’den 1,6 milyar TL’ye fırlar.

Kulağa harika geliyor, değil mi?

Ama unutmayın; aradaki o 800 milyon TL cebinize girmiş nakit para değildir, ekranda yeşil yanan bir kağıt üstü kardır. O karı gerçeğe dönüştürmek için malı satmanız gerekir.

Gelgelelim 100 milyon lotu tahtaya tek seferde boşaltmaya kalksanız, fiyat taban taban serbest düşüşe geçer, kar falan kalmaz.

İşte piyasada mal dağıtımı dediğimiz mekanizma burada başlar:

Önce fiyat yukarı taşınırken sosyal medyada ve kulislerde hisse hakkında müthiş hikayeler pompalanır.

Hisse tavan serileri yaparken arkadan “Treni kaçırıyorum” korkusuyla (FOMO) koşan binlerce heyecanlı alıcı gelir. O coşkulu alıcılar iştahla tahtaya hücum ederken, büyük pozisyon sahipleri fiyatı yukarılarda tutarak ellerindeki lotları parça parça piyasaya devreder.

Eğer bir hisse zirvelerde rekor hacimler yaparken, tavanlar bozup tekrar kilitlerken ana taşıyıcı kurumların saklamasındaki lotlar günbegün azalıyorsa, orada hisse yükselmiyor; eldeki mal yeni sahiplerine teslim ediliyordur.

4. Fiyat Tepe Taklak Olduğunda Ne Olur?

Mal dağıtımı tamamlandıktan ya da talep kesildikten sonra hissenin 16 TL’den 12 TL’ye gerilediğini düşünün. Zirveden %25 kayıp. Tepe fiyattan (16 TL) trene binen yatırımcı için bu korkunç bir zarardır.
Fiyat tekrar 8 TL maliyet seviyesine dönerse, tepeden alanın parası yarı yarıya erimiş olur. 8 TL’den pozisyon açan ana oyuncu ise hala ana parasını koruyordur.

İşte tam bu dip seviyelerde, 16 TL’den yakalanan küçük yatırımcıların bir kısmı artık dayanamaz. “Daha da batıyoruz, sıfırlanacak” paniğiyle zararına satış tuşuna basar.

Eğer tahtada başka bir grup veya aynı aktörler çıkıp bu panik satışlarını dipten sakince karşılıyor ve düşük fiyattan tekrar pay biriktirmeye başlıyorsa, buna da yeniden mal toplama denir.

Fakat burada da kendimize bir fren koymamız lazım: Her düşen hissede gizli bir plan, arkada çalışan bir “büyük akıl” aramak doğru değildir.

Bazen şirket berbat bir bilanço açıklar, bazen sektör krizine girer, bazen de yabancı fonlar koşulsuz satış yapar. Her düşüşe kulp takıp komplo teorisi üretmek yerine somut verilere bakmak gerekir.

5. Kurumların Takasındaki Milyonluk Lotlar Bize Ne Anlatır?

Sonunda başlangıçtaki o soruya geliyoruz:
“Falanca kurum 7-8 TL’den yüz milyon lot aldı, kesin gidecek miyiz?”
Cevap çok net: Hayır, kesinlikle yetmez.

Ben bir tahtada bu tarz hareketler gördüğümde kendime şu soruları sorarım:

Takas kalıcı mı?
O 100 milyon lotluk alımdan iki gün sonra, o kurumun takasında gerçekten bir artış var mı, yoksa mal gün içi işlemlerle başka yerlere mi paslandı?
İlk 5 kurum dengesi ne diyor?
Alıcı tarafı tek bir kurumda toplanırken, satışlar yüzlerce farklı küçük hesaba mı dağılmış (toplama işareti), yoksa tam tersi mi?
Fiyat neden patinaj çekiyor?
Tahtada rekor hacimler dönmesine rağmen hisse fiyatı birkaç kademe bile yukarı gidemiyorsa, biri orada güçlü alıcıya gizli gizli mal mı veriyor?
Virman trafiği var mı?
Bir kurumun takası boşalırken mal gerçekten satıldı mı, yoksa sadece yabancı ya da başka bir saklama hesabına virman mı yapıldı?

 

Bu sorulara yanıt vermeden sadece ekrandaki yeşil rakamlara veya devasa hacimlere bakıp işlem yapmak, sisli havada farları kapatıp araba sürmeye benzer.

Sözün Özü
Piyasada düşükten toplama, yukarıdan devretme ve dipten yeniden karşılama döngüsü teoride çok bilinen bir piyasa mekanizmasıdır.
Ancak bir hissede bu kurgunun döndüğünü iddia etmekle, gerçekten döndüğünü somut verilerle kanıtlamak bambaşka şeylerdir.
Hatta SPK da tam bu noktada çok net bir çizgi çeker: Fiyatı, miktarı ve emir hareketlerini yapay bir piyasa algısı yaratacak şekilde yönlendirmeyi işlem bazlı piyasa dolandırıcılığı (manipülasyon) sayar ve suç kabul eder.

Özetle; Borsada kimin ne kadar yüksek ses çıkardığına, gün içinde ekranda kaç milyon lot çevirdiğine aldanmayın. Seans bittiğinde malın kimin cebinde kaldığına, kimin gerçek risk aldığına ve o fiyatın arkasında sahici bir talep olup olmadığına bakın. Gözünüz gürültülü hacimde değil, sessizce yer değiştiren takasta olsun.

Borsada Takas Hareketlerini Okumak: Görünen Alıcı, Gerçek Maliyet ve Tahta Kontrolü

29 Ekim 2026 Borsa

Borsada derinlik ekranına baktığınızda milyonlarca lotluk yeşil emirler, tavan kovalayan aracı kurum dağılımları ve rekor kıran hacimler görebilirsiniz. Ancak günün sonunda tahtaya baktığınızda fiyatın yükselmek bir yana, kademe kademe gerilediğine şahit olursunuz.

Yatırımcıların en çok tuzağa düştüğü yer burasıdır: Yüksek hacim ve yüklü alımlar her zaman taze para girişini ya da yükseliş trendini göstermez.

Bu paradoksu çözebilmek için aracı kurum dağılımındaki (AKD) anlık alıcılara değil; malın gerçek sahibine, ilk maliyetine, takas virmanlarına ve işlem döngüsüne bakmak gerekir.

1. Görünmeyen Maliyet Avantajı: “10 TL Maliyetli Malın Gücü”

Bir hissenin halka arz veya toplama maliyetinin 10 TL olduğunu düşünelim. Hisse belirli bir süre yatayda veya baskı altında tutulur, küçük yatırımcının elindeki lotlar toplanır. Ardından tahta kademeli şekilde 70 TL seviyesine taşınır.

Piyasanın Gördüğü: 70 TL’den 50 milyon lotluk devasa bir işlem hacmi döner. Ekran başında “Kurumlar 70 TL’den deli gibi mal topluyor, hedef 120 TL” algısı oluşturulur.

Perde Arkası: Bu malı 70 TL’den satan elin gerçek maliyeti 10 TL’dir. 50 milyon lotun 70 TL ortalamayla boşaltılması, masaya yaklaşık 3,5 milyar TL brüt nakit koyar. İlk maliyet (500 milyon TL) düşüldüğünde elde edilen net kar potansiyeli muazzamdır.

Gerçek: Fiyat 70 TL’den 62 TL’ye, oradan 50 TL’ye gerilese bile o satıcı için fark etmez; çünkü her kademede katbekat kardadır. 68 TL’den “kurumla birlikte maliyetlendim” sanan yatırımcı paniklerken, satıcı elindeki devasa nakit gücüyle tahtayı istediği gibi baskılamaya ve fiyatı aşağı çekmeye devam eder.

2. Cep-to-Cep (Karşılıklı) İşlemler ve Sahte Derinlik

Bir hissede gün içinde 20 milyon lot alım yapıldığını görürsünüz. İlk 5 kurum net alıcı görünür, fakat hisse eksi kapatır.

Örnek Senaryo: X Kurumu 10 milyon lot alır, Y Kurumu 10 milyon lot satar. Ertesi gün tam tersi gerçekleşir veya takas günü (T+2) geldiğinde malların tek bir ana saklama hesabına (virmanla) aktarıldığı görülür.

Amaç: Piyasada “Burada büyük bir hikaye var, mal kapışılıyor” algısı yaratıp yapay hacimle hisseyi tarama listelerine ve hacim liderleri tablosuna sokmaktır. Bu suni likidite, içerideki gerçek satıcının elindeki malı piyasaya sessizce sindirmesi için gereken alıcı kitlesini çeker.

3. Fon ve Kurum Dolandırma Döngüsü: “Temiz Takas Yanılsaması”

Milyonlarca lotluk satış doğrudan piyasaya boca edilmez; çünkü bu durum tahtayı kilitler ve satıcının kendi ayağına sıkması anlamına gelir. Bunun yerine mal kademeli bir köprüden geçirilir:

Köprüye Aktarım: Ana aktör, elindeki yüklü blok malı özel emirle ya da borsa dışı anlaşmalarla belirli serbest/özel fonlara devreder.

Dağıtım: Fon veya anlaşmalı hesaplar, hisseyi gün içi volatilite yaratarak piyasa geneline parça parça yayar.

Sonuç: Takasa baktığınızda tek bir satıcı göremezsiniz; satışlar “Diğer” kalemine veya çok sayıda aracı kuruma homojen yayılmış görünür. Alıcı tarafında ise birkaç hevesli kurum tek başına kalır ve fiyat aşağı doğru süzülür.

4. VİOP ve Arbitraj Baskısı: “Spot Alınırken Fiyat Neden Düşer?”

Özellikle endeks ağırlığı yüksek derin tahtalarda sıkça yaşanan bir diğer senaryo spot-vadeli arbitrajıdır:

Mekanizma: Bir piyasa yapıcı veya arbitraj fonu, spot piyasadan milyonlarca lot hisse alırken, eşzamanlı olarak VİOP (Vadeli İşlem ve Opsiyon Piyasası) tarafında aynı miktarda kısa (short) pozisyon açar.

Yanılgı: Yatırımcı yalnızca spot tahtadaki milyonluk alımları izler ve yukarı yönlü bir ralli bekler. Oysa bu alım bir yön beklentisi değil; faiz veya fiyat makasından risksiz getiri sağlama amaçlı mekanik bir dengedir. Arbitraj kapandığında veya piyasa satıcılı olduğunda o spot alımlar fiyatı yukarı taşımaya yetmez.

5. Likidite ve Dayanıklılık Asimetrisi: Kim Satmak Zorunda?

Aynı tahtada yan yana oturan iki yatırımcının psikolojisi ve dayanıklılığı asla eşit değildir.

Fiyat geriledikçe, tepeden alan kredili hesaplar teminat tamamlama çağrılarıyla zorunlu satışa geçer. Bu zorunlu satışlar tahtaya geldikçe, milyonluk alımlar olsa bile satış dalgası alıcıları ezer geçer.

Borsada aracı kurum dağılımı (AKD) yalnızca günün trafiğini gösterir; takas ise o trafiğin tapusudur.

Bir tahtada milyonlarca lot el değiştirirken fiyat düşüyorsa, sahnelenen hacme değil; masadan karını alıp kalkan oyuncuların arkasında bıraktığı likidite boşluğuna bakmak gerekir. Gerçek kazanç, görünen alımlara kapılmakta değil; malın kaynağını, maliyet tabanını ve kimin satmak zorunda olduğunu doğru okumakta yatar.

Fon ve sermaye piyasalarında yaşanan likidite krizi, tasfiye süreci

20 Eylül 2026 Borsa



Piyasalarda son derece sıcak, sarsıcı ve geniş kitleleri doğrudan etkileyen bir kriz sürecinden geçiyoruz. Yaşananlar bir günde ortaya çıkmadı; temelleri geçmişe dayanan, uyarılara rağmen büyüyen ve en sonunda kaçınılmaz olarak patlak veren bir tablonun sonuçlarıyla yüzleşiyoruz. Süreci, nedenlerini, kurumların müdahalelerini ve bundan sonra bizi neyin beklediğini tüm detaylarıyla aktarmak istiyorum.

1. Krizin Arka Planı: Mekanizma Nasıl İşledi?

Bu krizin temelinde, bazı portföy yönetim şirketlerinin fonları aracılığıyla kurduğu sentetik getiri mekanizması yatıyor.

Olayın özeti şu:
Sığ Hisselerde Fiyat Manipülasyonu: Dolaşımdaki payı son derece düşük olan hisselerin payları fonlar üzerinden toplandı, piyasadaki likiditesi iyice daraltıldı ve küçük hacimlerle fiyatları astronomik seviyelere çekildi. Öyle ki F/K (Fiyat/Kazanç) oranları 150-160 seviyelerine kadar tırmandı; gerçek şirket değerlemeleriyle hiçbir bağı kalmayan fiyatlamalar oluştu.

Pay Karşılığı Repo ve Yapay Teminat: Fonlar, şişirdikleri bu hisseleri teminat göstererek pay karşılığı repo işlemleri yaptı ve borçlandı. Hisse fiyatı yukarı çıktıkça teminat değeri arttı; teminat değeri arttıkça fonun getirisi piyasa ortalamasının çok üzerine çıktı.

Risk Profili Maskelemesi: Bu işlemler sadece yüksek riskli serbest fonlarda değil, TEFAS’ta risk değeri 1 veya 2 olarak görünen para piyasası fonlarında da gizli bir risk olarak taşındı. Fon portföyünde “ters repo” görünüyordu; ancak bu ters repo devlet tahvili ya da hazine bonosu değil, sığ ve yapay biçimde şişirilmiş hisse senetlerine dayalıydı.

FOMO ve Sosyal Medya Güruhu: Yüksek enflasyon ortamında parasının değerini korumak isteyen küçük yatırımcı, aylık %1 bile olsa piyasa üstü getiri vadeden bu fonlara akın etti. Bu yönlendirmeyi bilinçli olarak körükleyen, eleştirenleri ve uyaranları linç eden organize bir sosyal medya faaliyeti yürütüldü.

2. Kurumların Müdahalesi ve Tasfiye Kararı

Krizin boyutu artık saklanamaz hale geldiğinde ve yabancı yatırımcı kuruluşların (MSCI, FTSE gibi) piyasadaki bu anormalliklere dikkat çekmesiyle birlikte denetleyici otoriteler peş peşe adımlar attı..
Finansal İstikrar Kurulu ve Likidite Adımı: Bankaların borçlanma limitlerinde rahatlama sağlandı. Buradaki ana hedef, fon krizinin bankacılık sistemine ve genele sıçramasını (bulaş etkisini) engellemekti. Sermaye piyasalarının oksijeni likiditedir; likidite çekilirse sistem boğulur. Bu hamle sayesinde bankacılık endeksi hızla toparlanarak genel endekse destek verdi.

SPK Müdahalesi ve Tasfiye: SPK, aralarında Tera ve Pusula’nın da bulunduğu 7 portföy yönetim şirketinin fonlarını TEFAS işlemlerine kapattı ve toplamda 131 fon için tasfiye sürecini başlattı.

İşlem Yasakları: İlgili hisselerde (Katılımevim, Gündoğdu Gıda, Odine Teknoloji, Destek Finans vb.) manipülatif pozisyon alan onlarca portföy yöneticisine 2 yıllık işlem yasakları getirildi.

Sistemik Yayılmayı Önleme (Katılımevim Adımı): Katılım finansman tarafındaki kriz riskini izole etmek amacıyla, ABD’deki Silicon Valley Bank krizinde olduğu gibi, kamu gücü (Emlak Konut devreye sokularak) devreye alındı.

3. Tasfiye Süreci Nasıl İşleyecek? Yatırımcı Parasını Alabilecek mi?

Tasfiye kararı hukuki ve operasyonel olarak belirli kurallara tabidir. Süreç şu adımlarla ilerler.

  • Fonun portföyündeki tüm varlıklar (hisse, tahvil, mevduat) tespit edilir.
  • Varlıklar nakde çevrilir, alacaklar tahsil edilir.
  • Fonun borçları ve giderleri ödenir.
  • Kalan net bakiye, katılma payları oranında yatırımcılara dağıtılır.

 

Fon Türlerine Göre Risk ve Beklentiler
Geleneksel Para Piyasası Fonları (Büyük Banka İştirakleri): Ak Portföy, İş Portföy, Garanti vb. kurumların fonlarındaki ters repoların dayanağı Hazine tahvilleri ve sağlam şirket borçlanma araçlarıdır. Bu fonlarda toksik varlık bulunmadığı için kalıcı bir anapara kaybı riski olmaz, bunlarda süreç hızla normale dönecektir.

Krizdeki Para Piyasası Fonları (Örn: TP2 vb.): Varlık yapısı serbest fonlara göre görece daha likit olduğu için süreç uzasa ve faiz/vade kaybı yaşansa da anaparanın tamamının batması beklenmez; ancak temerrüt ve ödeme gecikmeleri kaçınılmaz olacaktır.

Hisse Yoğun ve Serbest Fonlar: Bu tarafta ciddi bir anapara kaybı kesinleşmiş durumdadır. Çünkü fon portföyündeki %20-25 ağırlığa sahip sığ hisseleri satmak istediğinde tahtada alıcı yoktur. Satış emri verildiği an bu hisseler taban serilerine başlayacak, gerçek değerine (belki onda birine) çekilecek ve fonun portföy değeri eriyecektir.

13:30 Valör Karmaşası ve Geri Ödeme Takvimi:
TEFAS’ta 13:30 valör atlatma sınırıdır. Önceden satış emri vermiş ve eşleşmesi gerçekleşmiş olanların hakları önceliklidir; fon varlığından ilk olarak bu ödemeler ayrılır. Ancak takas esasları değiştirilen fonlarda (örneğin TLY gibi), her gün fiyat açıklanması durdurulmuş, ayın 15. iş gününde tek fiyat açıklaması ve ardından 10 iş günü içinde ödeme takvimine geçilmiştir. Bu durum, emir veren yatırımcının parasını hangi fiyattan ve ne zaman alacağı konusunda en az 1-1.5 aylık bir belirsizlik ve ciddi nakit akışı tıkanıklığı yaratmaktadır.

4. Piyasalara, Borsaya ve Makro Ekonomiye Etkileri

Borsada Bulaş Riski ve Likit Varlık Satışları: Fonlar nakit yaratmak ve yükümlülüklerini karşılamak zorunda kaldıklarında, taban olan sığ hisseleri satamayacakları için portföylerindeki kaliteli, likit varlıkları (örneğin Aselsan, THY, Tüpraş, Astor vb.) satmak zorunda kalabilirler. Bu durum BIST üzerinde bir süre dalgalanma ve satış baskısı yaratacaktır.
Fon Dünyasına Güven Kaybı: Yatırımcı refleks olarak ayrım yapmadan tüm butik veya bağımsız portföy yönetim şirketlerinden kaçma eğilimine girebilir. Bu da sektörde konsolidasyonu zorunlu kılacaktır.

Borsanın Tepki Yükselişi:  BIST’in toparlanmasının ana sebebi krizin çözülmesi değil; otoritenin kangrenli kolu kesip atarak bankacılık sistemine likidite kalkanı sağlamasıdır.

Makro Boyut: Enflasyon ortamında vatandaşın döviz yerine Türk lirası varlıklarda kalmasını sağlayan en önemli enstrüman para piyasası fonlarıydı. Buradaki güven kaybı, dövize yönelimi tetikleyebilir ve oluşan zararların bir kısmının kamuya yansımasıyla bütçeye ek yük getirebilir. Fed’in faiz patikasında şahin kalmaya devam ettiği bir dış konjonktürde bu iç sarsıntı işleri daha da zorlaştırabilir.

Sonuç ve Değerlendirme
Sermaye piyasalarında birinci kural yatırımcının kendi riskini denetlemesidir. Piyasa ortalaması %3.5 getiri sunarken bir fon %4.3 veriyorsa, orada mutlaka gizlenmiş bir risk primi vardır. Kolay ve sorgulanmayan getiri arayışı maalesef acı bir tecrübeyle noktalanmaktadır.

Müdahaleler zamanlama açısından gecikmiş olsa da kapsam ve kararlılık açısından piyasanın tamamen kilitlenmesini engellemiştir. Bu süreç, piyasanın safralarını atması ve orta-uzun vadede daha rasyonel, şeffaf bir zemine oturması için ağrılı ama zorunlu bir normalleşme sürecidir.

Pusula Meselesi Sadece Bir Fon Meselesi mi?

16 Eylül 2026 BorsaPinFinansal, pusula, tera

Son günlerde Pusula Portföy ve bazı yatırım fonlarıyla ilgili gelişmeler, ilk bakışta birkaç fonun yaşadığı bir problem gibi görünüyor.

Ancak asıl dikkat edilmesi gereken konu, bu fonların hangi varlıklara yatırım yaptığı ve diğer finansal kuruluşlarla nasıl bağlantılarının bulunduğu.

Çünkü sorun yalnızca bir fonun zarar etmesi değil, oluşabilecek zararın başka kurumlara taşınıp taşınmayacağı.

Sistem nasıl çalışıyor?

Düşük halka açıklığa sahip bazı hisselerde fiyatların hızlı yükseldiğini düşünelim.

Bu hisseleri yüksek oranda taşıyan bir fonun getirisi de doğal olarak yükseliyor. Yüksek getiri yatırımcıların ilgisini çekiyor ve fona yeni para girişi başlıyor.

Ancak sistemin asıl sınavı para girişinde değil, para çıkışında yaşanıyor.

Çok sayıda yatırımcı aynı anda parasını çekmek istediğinde fon varlıklarını satmak zorunda kalabilir.

Buradaki sorun şu:

Portföyde görünen değer ile o varlığı gerçekten satabileceğiniz fiyat aynı olmayabilir.

Özellikle düşük likiditeli hisselerde büyük miktarda satış, fiyatı ciddi şekilde aşağı çekebilir.

Asıl risk burada başlıyor

Eğer bu hisseler başka finansal kuruluşlara verilen kredilerde teminat olarak kullanılmışsa, problem tek bir fonla sınırlı kalmayabilir.

Örneğin:

Fon → Hisse → Teminat → Finansman sağlayan kurum

şeklinde bir bağlantı olduğunu düşünelim.

Fon borcunu ödeyemezse, alacaklı kurum teminatı satmak zorunda kalabilir. Ancak teminatın piyasada beklenen değerde satılamaması yeni bir zarar ortaya çıkarabilir.

Böylece başlangıçtaki problem başka bir kurumun bilançosuna taşınmış olur.

Para piyasası fonları neden önemli?

Para piyasası fonları yatırımcılar tarafından genellikle daha likit ve düşük riskli araçlar olarak görülüyor.

Bu nedenle, eğer yaşanan sorunların bu fonlarla veya başka finansal yapılarla bağlantısı olduğu doğrulanırsa, konu daha geniş bir boyut kazanabilir.

Aynı şekilde (*)tasarruf finansman şirketlerinin de bu zincire herhangi bir şekilde maruz kalıp kalmadığı önem taşıyor.

Burada henüz kesin bir sonuç çıkarmak doğru değil. Bunun için kurumların bilançoları, portföyleri ve karşılıklı yükümlülüklerinin incelenmesi gerekiyor.

En büyük risk: Güven kaybı

Finansal piyasalarda bazen asıl sorun zararın kendisi değil, zararın başka kurumlara yayılmasıdır.

Bir yatırımcı satış yapar.

Onu gören başka bir yatırımcı da satışa geçer.

Ardından likidite ihtiyacı artar ve daha fazla varlık satılmaya başlanır.

Bu noktada sorun fiyat düşüşünden çıkar, güven ve likidite problemine dönüşebilir.

Ancak bunun tersi de mümkün. Yatırımcılar riskli gördükleri varlıklardan çıkıp daha likit ve finansal yapısı güçlü varlıklara yönelebilir.

Şimdi neye bakılmalı?

Önümüzdeki süreçte özellikle şu soruların cevapları önemli:

  • Fonların gerçek likiditesi ne kadar?
  • Portföylerde hangi hisseler ne kadar ağırlıkta?
  • Bu hisselerin fiili dolaşımı ne kadar?
  • Fonların diğer finansal kuruluşlarla bağlantıları var mı?
  • Hangi varlıklar teminat olarak kullanılmış?
  • Bu teminatların gerçekten ne kadar likit olduğu nedir?
  • Para piyasası fonları veya tasarruf finansman şirketlerinin bu yapıya maruziyeti var mı?

Bu sorular cevaplanmadan “tek bir fonun problemi” demek de, “sistemik kriz” demek de erken olur.

Sonuç

Pusula etrafındaki gelişmelerin gerçekten ne ölçüde büyük bir probleme dönüşebileceğini zaman ve resmi incelemeler gösterecek.

Fakat burada takip edilmesi gereken en önemli konu yalnızca fonların ne kadar zarar ettiği değil.

Zararın kimin bilançosunda kaldığı ve başka hangi kurumlara taşınabileceği.

Çünkü finansal piyasalarda bazen en büyük risk, ilk satış değildir.

İlk satışı gören ikinci yatırımcının “Ben de çıkayım” demesidir.

* Katılım Evim de  Tasarruf sahiplerinin parası fon üzerinden işlemlere konu edildi ise kamu zararı oluşmuş olabilir. 

Fonlarda Finansal Mühendislik, Sistemik Risk ve BIST 30

05 Eylül 2026 BorsaPinbist30, finansal mühendislik, fon, fonların uyum süreci, sistematik risk, sistemik risk, tera

Bugün piyasalarda yaşananları anlamak için biraz geriye, 2008 küresel finans krizine bakmak gerekiyor.

2008 yılında ABD’de başlayan mortgage krizi, kısa sürede küresel bir finansal krize dönüştü. Sistemin temelinde, konut kredilerinin menkul kıymetleştirilerek tekrar piyasaya satılması ve elde edilen kaynakla yeni kredilerin verilmesi bulunuyordu.

Başlangıçta oldukça kârlı görünen bu yapı zamanla daha da karmaşık hale geldi. Bankalar ve finans kuruluşları daha riskli kişilere kredi vermeye başladı. Verilen krediler çeşitli dilimlere ayrılıyor, düşük ve yüksek riskli bölümler farklı finansal ürünlere dönüştürülüyor ve bunlar tekrar piyasada satılıyordu.

Riskin paketlenmesi ve farklı finansal ürünlerin içerisine dağıtılması, sistemdeki gerçek riskin görünürlüğünü azaltıyordu. Üstelik bu ürünlerin bir kısmı sigortalanıyor, derecelendirme kuruluşlarından yüksek notlar alıyor ve böylece yatırımcı açısından olduğundan daha güvenli görünüyordu.

Konut fiyatları yükselmeye devam ettiği sürece sistem çalıştı.

Ancak faizlerin yükselmesi ve konut fiyatlarının düşmeye başlamasıyla birlikte zincir kırıldı. Teminatların değeri düştü, borçların karşılığı yetersiz kaldı ve finansal sistemin farklı noktalarındaki riskler aynı anda ortaya çıktı. Sonuçta Lehman Brothers gibi dev finans kuruluşlarının da dahil olduğu büyük bir kriz yaşandı.

Buradaki en önemli kavramlardan biri finansal mühendislik ve bunun oluşturabileceği sistemik risk.

Finansal mühendislik tek başına suç anlamına gelmiyor. Sistemde bulunan bir açığın veya düzenlemenin izin verdiği bir alanın kullanılması hukuken mümkün olabilir. Ancak bu davranış çok sayıda piyasa oyuncusu tarafından aynı anda kullanılmaya başladığında, tek tek bakıldığında sorun teşkil etmeyen işlemler birleşerek büyük bir sistemik riske dönüşebilir.

Türkiye’deki fon piyasasında yaşanan tartışmanın temelinde de buna benzer bir yapı bulunuyor.

Fonlar üzerinden oluşan risk

Fonların ayrı bir tüzel kişilik olarak değerlendirilmesi, portföy yöneticilerine yatırım kararlarında önemli bir hareket alanı sağlıyor.

Normal şartlarda bir kişinin kendi şirketinin hissesini alıp yükseltmesi, ardından piyasaya açıklamalar yaparak satması ciddi şekilde incelenecek bir işlem olur. İlişkili taraf ilişkisi, içeriden öğrenenlerin ticareti ve piyasa manipülasyonu gibi başlıklar gündeme gelebilir.

Fakat aynı işlemin bir fon üzerinden gerçekleştirilmesi durumunda yapı farklı bir hukuki görünüm kazanabiliyor.

Örneğin bir yatırımcı bir portföy yönetim şirketiyle anlaşarak bir fon kuruyor ve bu fon aracılığıyla kendi şirketinin hisselerini satın alıyor. Fon ayrı bir yapı olduğu için, işlemin arkasındaki ekonomik ilişkinin tespit edilmesi daha karmaşık hale geliyor.

Bu noktada ortaya çıkan temel sorun şu:

Bir işlemin hukuken mümkün olması, sistem açısından risksiz olduğu anlamına gelmiyor.

Fon belirli bir hisseyi yoğun şekilde almaya başladığında takas oranı yükseliyor, piyasadaki arz azalıyor ve hissenin fiyatı yukarı doğru hareket edebiliyor.

Fiyat yükseldikçe fonun getirisi artıyor.

Fonun getirisi arttıkça yatırımcı ilgisi artıyor.

Yeni yatırımcıların getirdiği para ile fonun büyüklüğü artıyor.

Fon büyüdükçe belirli hisselerdeki pozisyonların büyüklüğü de artabiliyor.

Böylece kendi kendini besleyen bir döngü ortaya çıkabiliyor.

Fon büyüdükçe sorun neden büyüyor?

Buradaki kritik nokta, fonun yüksek getiri üretmesi değil.

Sorun, yüksek getirinin hangi mekanizma üzerinden üretildiği.

Eğer fonun getirisi şirketlerin gerçek finansal performansından değil, piyasadaki sınırlı arz nedeniyle oluşan fiyat hareketlerinden besleniyorsa, ortaya yapay fiyat oluşumları çıkabilir.

Bir fonun belirli hisselerde aşırı yoğunlaşması, o hisselerdeki fiyat oluşumunu etkileyebilir. Aynı mekanizma çok sayıda fon tarafından kullanıldığında ise sorun tek bir hisse veya tek bir fon olmaktan çıkar ve piyasanın genel yapısını etkileyebilecek bir noktaya ulaşır.

İşte burada sistemik risk ortaya çıkar.

Asıl sorumluluk nerede?

Finansal sistemlerde düzenlemelerin temel amacı yalnızca suç işlendikten sonra cezalandırmak değildir.

Asıl amaç, sistemin içerisinde bulunan açıkların büyük bir probleme dönüşmesini önceden engellemektir.

ABD’deki mortgage krizinde de temel sorunlardan biri, sistemdeki risklerin uzun süre büyümesine izin verilmesiydi. Riskler farklı finansal ürünlerin içine dağıtıldı, görünmez hale geldi ve sistem büyüdükçe herkes kazandığını düşündü.

Ta ki zincirin bir halkası kırılana kadar.

Türkiye’deki fon piyasasında da benzer şekilde, belirli düzenlemelerin oluşturduğu boşlukların uzun süre kullanılmasının ileride sistemik bir probleme dönüşebileceği tartışılıyor.

Bu nedenle düzenlemelerin yalnızca “şu oranı geçemezsin” şeklinde yapılması yeterli olmayabilir. Önemli olan, ekonomik olarak aynı sonuca ulaşan işlemlerin farklı hukuki yapılar kullanılarak tekrar tekrar yapılmasının önüne geçebilmek.

Yeni düzenlemeler ve fonların uyum süreci

Fon piyasasında getirilen yeni kurallar, özellikle ilişkili taraf işlemleri ve belirli hisselerdeki yoğunlaşmalar açısından önemli bir değişim yaratıyor.

Ancak burada başka bir problem ortaya çıkıyor.

Düzenlemeler nedeniyle daha önce büyük pozisyonlar oluşturmuş fonların ellerindeki bazı hisseleri azaltmaları veya satmaları gerekebilir.

Bu durumda satış baskısı yalnızca şirketin temel performansından kaynaklanmaz.

Fonların mevzuata uyum sağlamak amacıyla gerçekleştirmek zorunda oldukları işlemler de fiyatları etkileyebilir.

Dolayısıyla bazı hisselerde yaşanan sert düşüşleri değerlendirirken yalnızca şirketin bilançosuna bakmak yeterli olmayabilir.

Takas yapısı, fonların sahip olduğu paylar, fiili dolaşım oranı ve fonların uyum sürecinde gerçekleştirmek zorunda kalabileceği işlemler de dikkate alınmalıdır.

BIST 30 neden önemli?

Bu süreçte BIST 30 kriterleri de ayrıca önem kazanıyor.

Endeks içerisinde yer alan şirketler, özellikle büyük kurumsal yatırımcılar ve fonlar açısından daha fazla önem taşıyor. Yeni kriterlerin hangi şirketleri endekse dahil edeceği veya hangi şirketleri dışarıda bırakacağı, fonların portföylerinde önemli değişikliklere yol açabilir.

Eğer yeni kurallar sonucunda fon piyasası birkaç büyük oyuncunun hakim olduğu bir yapıya dönüşürse, küçük ve orta ölçekli fonların rekabet etmesi zorlaşabilir.

Böyle bir durumda piyasanın giderek birkaç büyük kurumsal oyuncunun kontrolünde yoğunlaşması, yani bir tür oligarklaşma, gündeme gelebilir.

Öte yandan fonların zorunlu satışları nedeniyle bazı hisselerde aşırı fiyat bozulmaları oluşmuşsa, uyum sürecinin tamamlanmasının ardından bunun tersine bir süreç de yaşanabilir.

Peki bundan sonra ne olabilir?

En önemli ihtimal, fonların zorunlu satışları nedeniyle gerçek değerlerinin altında fiyatlanan şirketlerin ortaya çıkması.

Burada her düşen hisseyi “ucuz” olarak değerlendirmek doğru olmaz.

Önemli olan, fiyatı düşen şirket ile değeri düşen şirket arasındaki farkı ortaya koyabilmek.

Şirketin faaliyetleri güçlü, bilançosu sağlam ve gelecekteki kârlılık potansiyeli devam ediyorsa; buna karşın fiyatı yalnızca fonların pozisyon azaltması nedeniyle baskı altında kalıyorsa, ortaya önemli fırsatlar çıkabilir.

Bunun tam tersi de mümkün.

Gerçekten temel problemi bulunan ve fiyatı düşmesi gereken şirketlerin yalnızca fon satışları nedeniyle düştüğünü düşünerek alım yapmak ciddi bir hata olabilir.

Bu nedenle önümüzdeki dönemde yalnızca fiyat hareketlerini değil;

  • fonların takas paylarını,
  • ilişkili taraf durumlarını,
  • fiili dolaşım oranlarını,
  • fonların hangi hisselerde yoğunlaştığını,
  • BIST 30 değişikliklerini,
  • yeni düzenlemelerin fonlar üzerindeki etkisini,
  • şirketlerin gerçek finansal performansını

birlikte değerlendirmek gerekiyor.

Sonuç olarak piyasanın önündeki en önemli konu yalnızca fonların satış yapması değil.

Asıl mesele, finansal mühendislik yoluyla oluşturulabilecek risklerin sistemik bir probleme dönüşmesini engelleyecek sağlıklı bir piyasa yapısının kurulması.

Eğer bu süreç doğru yönetilirse, bugün zorunlu satışlar nedeniyle baskı altında kalan bazı kaliteli şirketler ilerleyen dönemde gerçek değerlerine doğru yeniden fiyatlanabilir.

Bu nedenle önümüzdeki dönemde özellikle BIST 30 değişiklikleri, fonların uyum süreci ve takas hareketleri yakından takip edilmeli.

BorsaPin Frama Strateji Algoritması (TradingView)

30 Nisan 2026 İndikatör, Pine Script, Teknik Analiz, Trading Viewalgoritmik trading, borsa strateji geliştirme, Borsa trading stratejileri, BorsaPin stratejisi, FRAMA nedir, FRAMA stratejisi, hisse senedi alım satım stratejisi, momentum stratejisi, otomatik trading sistemi, Pine Script strateji, Supertrend nasıl kullanılır, Supertrend stratejisi, teknik analiz göstergeleri, TradingView strateji kodu, trend takip stratejisi

Herkese Merhaba, Uzun zamandır blog yazısı paylaşmıyordum, trading view için geliştirdiğim strateji koduyla dönelim dedik.
Şimdi borsapin frama stratejisi, trend takibini daha “akıllı” hale getirmek için iki güçlü yaklaşım kullanıyor.  FRAMA (Fractal Adaptive Moving Average) ve Supertrend. Amaç, piyasadaki gürültüyü filtreleyip yalnızca güçlü ve sürdürülebilir trendlere girmek.

Stratejinin temelinde üç katmanlı bir filtreleme var. İlk olarak haftalık zaman diliminde FRAMA’nın yukarı eğimli olması gerekiyor. Bu, büyük resimde piyasanın gerçekten yükseliş trendinde olduğunu doğrular ve yatay piyasaları büyük ölçüde eler. Ardından günlük grafikte fiyatın FRAMA’nın üzerinde olması ve aynı zamanda FRAMA’nın yukarı yönlü olması gerekiyor. Son olarak ise Supertrend göstergesinin alış sinyali üretmesiyle bu üç koşul birlikte sağlandığında sistem “onaylı” bir long pozisyon açıyor.
Çıkış tarafında ise aceleci davranılmıyor. Günlük FRAMA’nın altına iniş tek başına yeterli değil; belirli sayıda bar boyunca bu zayıflığın devam etmesi gerekiyor. Buna ek olarak Supertrend’in satış sinyali vermesiyle birlikte pozisyon kapatılıyor.

Buradaki yaklaşım, ani dalgalanmalarda gereksiz çıkışları azaltmak,  kısa vadeli gürültüyü filtreleyip orta-uzun vadeli trendleri yakalamaya odaklanıyoruz, disiplinli bir trend takip sistemi size sunar.. Özellikle “trend varsa kal, yoksa uzak dur” yada “düşen bıçağı tutma” mantıklarından esinlenildi. 

// @frama & Supertrend - BorsaPin Kursatsenturk.com
// Giriş: Haftalık Yukarı Eğimli olacak + Günlük FRAMA  AL sinyali verecek + Supertrend AL
// Çıkış: Günlük FRAMA (Teyitli) + Supertrend SAT

//@version=5
strategy("@frama BorsaPin Stratejisi", overlay=true, initial_capital=10000, 
     default_qty_type=strategy.percent_of_equity, default_qty_value=100,
     process_orders_on_close=true)

// ═══════════════════════════════════════════════════════════════
// GİRDİLER
// ═══════════════════════════════════════════════════════════════
grp_date = "Backtest Tarih Aralığı"
startDate = input.time(timestamp("2024-01-01 00:00 +0300"), "Başlangıç", group=grp_date)
endDate   = input.time(timestamp("2026-12-31 23:59 +0300"), "Bitiş", group=grp_date)
isInDate_Range = time >= startDate and time <= endDate

grp_params = "Gösterge Ayarları"
frama_len    = input.int(16,  "FRAMA Uzunluk", group=grp_params)
fc           = input.int(1,   "Hızlı Periyot (FC)", group=grp_params)
sc           = input.int(200, "Yavaş Periyot (SC)", group=grp_params)
st_len       = input.int(10,  "Supertrend Periyot", group=grp_params)
st_mult      = input.float(3.4, "Supertrend Çarpan", step=0.1, group=grp_params)

grp_logic = "Giriş ve Çıkış Filtreleri"
slope_thresh = input.float(0.1, "Haftalık Min. Eğim % (Yatay Filtresi)", step=0.01, group=grp_logic)
confirm_bars = input.int(3, "Satış Öncesi Bekleme (Bar Sayısı)", minval=1, group=grp_logic)

// ═══════════════════════════════════════════════════════════════
// Frama Hesaplama Fonksiyonu
// ═══════════════════════════════════════════════════════════════
f_frama(_src, _len, _fc, _sc) =>
    float _frama = na
    _half = _len / 2
    _n1 = (ta.highest(high, _half) - ta.lowest(low, _half)) / _half
    _n2 = (ta.highest(high[_half], _half) - ta.lowest(low[_half], _half)) / _half
    _n3 = (ta.highest(high, _len) - ta.lowest(low, _len)) / _len
    _dimen = (_n1 > 0 and _n2 > 0 and _n3 > 0) ? (math.log(_n1 + _n2) - math.log(_n3)) / math.log(2) : 1.0
    _w = math.exp(-4.6 * (_dimen - 1))
    _sc_a = 2.0 / (_sc + 1), _fc_a = 2.0 / (_fc + 1)
    _alpha = math.max(_sc_a, math.min(_fc_a, _w * (_fc_a - _sc_a) + _sc_a))
    _frama := na(_frama[1]) ? _src : (_alpha * _src) + ((1.0 - _alpha) * nz(_frama[1], _src))
    [_frama, _frama > nz(_frama[1], 0)]

// ═══════════════════════════════════════════════════════════════
// Hesaplamalar
// ═══════════════════════════════════════════════════════════════
// 1. Haftalık Frama (10 İşlem Günü / 2 Hafta Modu)
[wf_val, wf_up] = request.security(syminfo.tickerid, "W", f_frama(hlc3, frama_len, fc, sc), lookahead=barmerge.lookahead_on)
wf_slope_pct = ((wf_val - nz(wf_val[1])) / nz(wf_val[1])) * 100
wf_strict_up = wf_up and wf_slope_pct > slope_thresh // Yatay piyasa filtresi

// 2. Günlük Frama
[f_val, f_up] = f_frama(hlc3, frama_len, fc, sc)

// 3. Günlük Supertrend
[st_val, st_dir] = ta.supertrend(st_mult, st_len)
st_buy = st_dir == -1

// ═══════════════════════════════════════════════════════════════
// Mantık
// ═══════════════════════════════════════════════════════════════
// Giriş: Haftalık Eğim + Günlük Frama Üstü + Supertrend Yeşil
long_entry = wf_strict_up and close > f_val and st_buy

// ÇIKIŞ: Günlük Frama Altı (onaylı) + Supertrend Kırmızı
var int bars_below_frama = 0
bars_below_frama := (close < f_val or not f_up) ? bars_below_frama + 1 : 0
long_exit = (bars_below_frama >= confirm_bars) and (st_dir == 1)

// ═══════════════════════════════════════════════════════════════
// Görseller
// ═══════════════════════════════════════════════════════════════
// Haftalık (Mavi), Günlük (Yeşil/Kırmızı), Supertrend  
plot(wf_val, "Haftalık Kilit", color=wf_strict_up ? color.blue : color.gray, linewidth=4)
plot(f_val, "Günlük Frama", color=f_up ? color.green : color.red, linewidth=2)
plot(st_val, "Supertrend", color=st_buy ? color.teal : color.orange, style=plot.style_linebr)

// Mum Boyama
bar_color = long_entry ? #00ff88 : (strategy.position_size > 0 and not long_exit ? #9ea4ad : #ff0044)
barcolor(bar_color)

// ═══════════════════════════════════════════════════════════════
// Emirler
// ═══════════════════════════════════════════════════════════════
if isInDate_Range
    if long_entry
        strategy.entry("Long", strategy.long, comment="Onaylı AL")
    
    if long_exit and strategy.position_size > 0
        strategy.close("Long", comment="Onaylı Çıkış")

 

Bu strateji güçlü bir trend takip sistemi olsa da, bazı önemli sakıncaları ve dikkat edilmesi gereken noktalar var.
Öncelikle FRAMA ve Supertrend gibi trend bazlı göstergeler, yatay (sideways) piyasalarda gecikmeli ve yanıltıcı sinyaller üretir. Özellikle trend oluşmadan önce yapılan girişler küçük geri çekilmelerde stop olma riskini artırır.
Haftalık filtre bu riski azaltmaya çalışsa da tamamen ortadan kaldırmayabilir. İkinci olarak, strateji gecikmeli (lagging) bir yapıya sahip. Yani fiyat hareketini önceden tahmin etmekten çok, oluşmuş trendi takip eder. Bu durum güçlü trendlerde avantaj sağlarken, hızlı dönüşlerde geç kalmaya neden olabilir.

Ayrıca Supertrend ve FRAMA birlikte kullanıldığı için bazı dönemlerde fazla filtreleme (over-filtering) oluşabilir ve bu da işlem sayısını ciddi şekilde azaltır. Bu, performansı artırabilir ama fırsat kaçırma riskini de beraberinde getirir. Son olarak, bu tür sistemler geçmiş veride iyi sonuç verse bile, piyasa rejimi değiştiğinde (volatilite, haber akışı, kriz dönemleri) performansları farklılaşır. Bu nedenle bu stratejiyi  tek başına karar sistemi olarak değil, mutlaka risk yönetimi ve portföy çeşitlendirmesi ile birlikte kullanılmalı. Fundamental analizler, diğer tekniklerle desteklenmeside önemlidir.

Python ile Otomatik EMA Sinyal Analizi: Kısa, Orta ve Uzun Vadeli Alım Stratejileri

11 Ağustos 2025 BorsaPin, Python, Teknik Analizalgoritmik trading, alım satım sinyalleri, borsa, borsa otomasyonu, Ema, excel raporlama, hisse senedi analizi, kısa vade, orta vade, otomatik analiz, pin bar, Pine Script, Python, sinyal takibi, Teknik Analiz, trend takibi, üssel hareketli ortalama, uzun vade, yatırım stratejisi


Betik Güncellendi 16.08.25 v1.02



Bu Python kodu, hisse senedi yatırımcıları için tasarlanmış, EMA (Üssel Hareketli Ortalama) tabanlı bir sinyal analiz sistemidir. Kod, her hisse için farklı vadelere özel sinyal üretir ve bu sinyallerin nasıl oluşup sonlandığını titizlikle takip eder.

Kodun kısa, orta ve uzun vadeli sinyal mantığına dair detaylar şu şekilde


Kısa Vade Sinyalleri (EMA 5, 8, 13, 21)

  • AL (Alım) Sinyalinin Oluşumu: Kısa vadeli bir alım sinyali, kapanış fiyatının 5, 8, 13 ve 21 günlük EMA’ların üzerinde olması ve aynı zamanda bu dört EMA’nın da bir önceki güne göre yükseliş eğiliminde olmasıyla başlar. Bu koşul, güçlü bir yukarı yönlü momentumun başladığına işaret eder.
  • AL Sinyalinin Devamı: Sinyal bir kez “AL” olarak belirlendikten sonra, kapanış fiyatı 21 günlük EMA’nın üzerinde kaldığı sürece sinyal devam eder ve “Sinyal Süresi” sayacı artmaya devam eder.
  • SAT (Satım) Sinyalinin Oluşumu: Fiyat 21 günlük EMA’nın altına düştüğünde, “AL” sinyali sonlanır ve “SAT” sinyali oluşur. Bu durum, kısa vadeli yükseliş trendinin zayıfladığını gösterir.

Orta Vade Sinyalleri (EMA 34, 55)

  • AL (Alım) Sinyalinin Oluşumu: Orta vadeli alım sinyali için fiyatın hem 34 hem de 55 günlük EMA’ların üzerinde olması ve 34 günlük EMA’nın 55 günlük EMA’yı yukarı keserek trendin yükselişe geçtiğini teyit etmesi gerekir.
  • SAT (Satım) Sinyalinin Oluşumu: Fiyat 55 günlük EMA’nın altına düştüğü anda, “AL” sinyali sonlanır ve “SAT” sinyali oluşur.

Uzun Vade Sinyalleri (EMA 89, 144)

  • AL (Alım) Sinyalinin Oluşumu: Uzun vadeli alım sinyali, kapanış fiyatının hem 89 hem de 144 günlük EMA’ların üzerinde olmasıyla oluşur. Bu, hissenin uzun vadeli bir yükseliş trendinde olduğunu gösterir.
  • SAT (Satım) Sinyalinin Oluşumu: Fiyat 144 günlük EMA’nın altına indiğinde, uzun vadeli trendin tehlikeye girdiğini belirten “SAT” sinyali oluşur.

Python Kodu, Daha önce oluşturduğumuz python StokData/Kapanis klasöründe bulunan hisselerin kapanış datalarını kullanır. Seans kapanışından sonra kodu çalıştırdığınızda Ema sinyallerini oluşturur, bu sinyallerin durumlarını analiz eder güncel durumu raporlar. Bu rapor, hisselerin son sinyalini, sinyalin kaç gündür aktif olduğunu ve bu süreçteki kar/zarar durumunu net bir şekilde gösterir. Bu sayede yatırımcılar, hangi hisselerin hangi trendde olduğunu kolayca anlayabilir ve buna göre pozisyonlarını yönetebilir.


Örnek Excel Çalışması 
BorsaPin_EMA_Analizleri

X_06_BorsaPin_EmaSinyals.py olarak adlandırdım. Ver.1.02 Güncellndi
Kısa orta ve uzun vade de al sat bekle gibi sinyalleri Excel'e dökümünü yapacaktır.

Python Betiğimize ait kod

import pandas as pd
import os
import warnings
from datetime import datetime
from colorama import Fore, init
import glob
from typing import List, Dict, Any, Optional
from openpyxl import load_workbook
from openpyxl.utils.dataframe import dataframe_to_rows
from openpyxl.styles import PatternFill, Font, Alignment, Border, Side
from openpyxl.formatting.rule import ColorScaleRule

"""
      Borsapin StokData/Kapanis klasöründeki hisse datalarından 
      Kısa, orta,uzun vade al sat tut gibi sinyalleri excele aktarır.
      Pine Script™'e EMA Sinyal Tablosu indikatörümüze göre güncellenmiş kurallar ile
      Sinyal bozulma uyarıları eklendi 
      Ver 1.02 
      www.kursatsenturk.com

      """

# Uyarıları kapat
warnings.filterwarnings('ignore')
init(autoreset=True)


class BorsaPinEMAAnalyzer:
    def __init__(self):
        self.ema_periods = {
            'kisa_vade': [5, 8, 13, 21],
            'orta_vade': [34, 55],
            'uzun_vade': [89, 144]
        }
        self.successful_files: List[str] = []
        self.failed_files: List[str] = []

    @staticmethod
    def calculate_ema(data: pd.Series, period: int) -> pd.Series:
        """EMA hesaplama fonksiyonu"""
        return data.ewm(span=period, adjust=False).mean()

    @staticmethod
    def load_stock_data(file_path: str) -> pd.DataFrame:
        """Hisse verilerini Excel dosyasından yükleme"""
        try:
            df = pd.read_excel(file_path)

            required_columns = ['Tarih', 'Kapanış']
            missing_columns = [col for col in required_columns if col not in df.columns]
            if missing_columns:
                raise ValueError(f"Excel dosyasında eksik sütunlar: {missing_columns}")

            df['Tarih'] = pd.to_datetime(df['Tarih'])
            df = df.sort_values('Tarih').reset_index(drop=True)
            return df

        except (FileNotFoundError, ValueError, pd.errors.ParserError) as e:
            print(f"{Fore.RED}❌ Veri yükleme hatası: {e}")
            return pd.DataFrame()

    def calculate_all_emas(self, df: pd.DataFrame) -> pd.DataFrame:
        """Tüm EMA'ları hesapla"""
        close_prices = df['Kapanış']

        all_periods = self.ema_periods['kisa_vade'] + self.ema_periods['orta_vade'] + self.ema_periods['uzun_vade']

        for period in all_periods:
            if len(df) >= period:
                df[f'EMA{period}'] = self.calculate_ema(close_prices, period)
            else:
                df[f'EMA{period}'] = pd.NA
        return df

    @staticmethod
    def check_signal_deterioration(df: pd.DataFrame, i: int) -> Dict[str, str]:
        """Sinyal bozulma durumlarını kontrol et"""
        warnings = {
            'kisa_uyari': '',
            'orta_uyari': '',
            'uzun_uyari': ''
        }

        if i < 1:  # En az 1 önceki veri gerekli
            return warnings

        kapanis = df.loc[i, 'Kapanış']

        # KISA VADE UYARILARI
        if all(pd.notna(df.loc[i, col]) for col in ['EMA5', 'EMA8', 'EMA13', 'EMA21']) and \
                all(pd.notna(df.loc[i - 1, col]) for col in ['EMA5', 'EMA8', 'EMA13', 'EMA21']):

            ema5, ema8, ema13, ema21 = df.loc[i, 'EMA5'], df.loc[i, 'EMA8'], df.loc[i, 'EMA13'], df.loc[i, 'EMA21']
            ema5_once, ema8_once, ema13_once = df.loc[i - 1, 'EMA5'], df.loc[i - 1, 'EMA8'], df.loc[i - 1, 'EMA13']

            # Önce durum kontrolü yap
            kisa_durum = df.loc[i, 'Kisa_Durum'] if 'Kisa_Durum' in df.columns else 'BEKLE'
            kisa_durum_once = df.loc[i - 1, 'Kisa_Durum'] if i > 0 and 'Kisa_Durum' in df.columns else 'BEKLE'

            # AL sinyali varken 21 EMA altına sarktığında
            if kisa_durum == 'AL' and kapanis < ema21:
                warnings['kisa_uyari'] = "⚠️ 21 EMA Altına Sarkma"
            # AL sinyali varken 5, 8, 13 EMA'da aşağı eğim başladığında (sinyal bozulmaya başladı)
            elif kisa_durum == 'AL' and (ema5 < ema5_once and ema8 < ema8_once and ema13 < ema13_once):
                warnings['kisa_uyari'] = "⚠️ EMA Eğim Bozulması"

        # ORTA VADE UYARILARI
        if all(pd.notna(df.loc[i, col]) for col in ['EMA34', 'EMA55']) and i > 0 and \
                all(pd.notna(df.loc[i - 1, col]) for col in ['EMA34', 'EMA55']):

            ema34 = df.loc[i, 'EMA34']
            ema55 = df.loc[i, 'EMA55']
            ema34_once = df.loc[i - 1, 'EMA34']
            ema55_once = df.loc[i - 1, 'EMA55']

            orta_durum = df.loc[i, 'Orta_Durum'] if 'Orta_Durum' in df.columns else 'BEKLE'
            orta_durum_once = df.loc[i - 1, 'Orta_Durum'] if i > 0 and 'Orta_Durum' in df.columns else 'BEKLE'

            # AL sinyali varken 34 EMA altında kapatmalarda
            if orta_durum == 'AL' and kapanis < ema34:
                warnings['orta_uyari'] = "⚠️ 34 EMA Altında Kapanış"
            # AL sinyali varken 34 ve 55 EMA'da aşağı eğim (sinyal bozulmaya başladı)
            elif orta_durum == 'AL' and (ema34 < ema34_once and ema55 < ema55_once):
                warnings['orta_uyari'] = "⚠️ EMA Eğim Bozulması"

        # UZUN VADE UYARILARI
        if all(pd.notna(df.loc[i, col]) for col in ['EMA89', 'EMA144']) and i > 0 and \
                all(pd.notna(df.loc[i - 1, col]) for col in ['EMA89', 'EMA144']):

            ema89 = df.loc[i, 'EMA89']
            ema144 = df.loc[i, 'EMA144']
            ema89_once = df.loc[i - 1, 'EMA89']
            ema144_once = df.loc[i - 1, 'EMA144']

            uzun_durum = df.loc[i, 'Uzun_Durum'] if 'Uzun_Durum' in df.columns else 'BEKLE'
            uzun_durum_once = df.loc[i - 1, 'Uzun_Durum'] if i > 0 and 'Uzun_Durum' in df.columns else 'BEKLE'

            # AL sinyali varken 89 EMA altına sarkmada
            if uzun_durum == 'AL' and kapanis < ema89:
                warnings['uzun_uyari'] = "⚠️ 89 EMA Altına Sarkma"
            # AL sinyali varken 89 ve 144 EMA'da aşağı eğim (sinyal bozulmaya başladı)
            elif uzun_durum == 'AL' and (ema89 < ema89_once and ema144 < ema144_once):
                warnings['uzun_uyari'] = "⚠️ EMA Eğim Bozulması"

        return warnings

    def determine_signal_status(self, df: pd.DataFrame) -> pd.DataFrame:
        """Sinyal durumlarını belirle - Pine Script™'e kurallar güncellendi 16.08.25"""
        df['Kisa_Durum'] = 'BEKLE'
        df['Orta_Durum'] = 'BEKLE'
        df['Uzun_Durum'] = 'BEKLE'
        df['Kisa_Bar_Sayaci'] = 0
        df['Orta_Bar_Sayaci'] = 0
        df['Uzun_Bar_Sayaci'] = 0
        df['Kisa_Sinyal_Tarihi'] = pd.NaT
        df['Orta_Sinyal_Tarihi'] = pd.NaT
        df['Uzun_Sinyal_Tarihi'] = pd.NaT
        df['Kisa_Sinyal_Fiyati'] = pd.NA
        df['Orta_Sinyal_Fiyati'] = pd.NA
        df['Uzun_Sinyal_Fiyati'] = pd.NA

        # Yeni uyarı sütunları
        df['Kisa_Uyari'] = ''
        df['Orta_Uyari'] = ''
        df['Uzun_Uyari'] = ''

        if len(df) < 2:
            return df

        for i in range(1, len(df)):
            kisa_durum_once = df.loc[i - 1, 'Kisa_Durum']
            orta_durum_once = df.loc[i - 1, 'Orta_Durum']
            uzun_durum_once = df.loc[i - 1, 'Uzun_Durum']

            kapanis = df.loc[i, 'Kapanış']

            # KISA VADE SİNYALLERİ - Pine Script™ indikatörümüzle uyumlu
            if all(pd.notna(df.loc[i, col]) for col in ['EMA5', 'EMA8', 'EMA13', 'EMA21']) and \
                    all(pd.notna(df.loc[i - 1, col]) for col in ['EMA5', 'EMA8', 'EMA13', 'EMA21']):

                ema5, ema8, ema13, ema21 = df.loc[i, 'EMA5'], df.loc[i, 'EMA8'], df.loc[i, 'EMA13'], df.loc[i, 'EMA21']

                kisa_al_kosulu = (kapanis > ema5 and kapanis > ema8 and kapanis > ema13 and kapanis > ema21)
                kisa_egim_yukari = (ema5 > df.loc[i - 1, 'EMA5'] and ema8 > df.loc[i - 1, 'EMA8'] and
                                    ema13 > df.loc[i - 1, 'EMA13'] and ema21 > df.loc[i - 1, 'EMA21'])

                if kisa_al_kosulu and kisa_egim_yukari:
                    df.loc[i, 'Kisa_Durum'] = "AL"
                    if kisa_durum_once != "AL":
                        df.loc[i, 'Kisa_Bar_Sayaci'] = 1
                        df.loc[i, 'Kisa_Sinyal_Tarihi'] = df.loc[i, 'Tarih']
                        df.loc[i, 'Kisa_Sinyal_Fiyati'] = df.loc[i, 'Kapanış']
                    else:
                        df.loc[i, 'Kisa_Bar_Sayaci'] = df.loc[i - 1, 'Kisa_Bar_Sayaci'] + 1
                        df.loc[i, 'Kisa_Sinyal_Tarihi'] = df.loc[i - 1, 'Kisa_Sinyal_Tarihi']
                        df.loc[i, 'Kisa_Sinyal_Fiyati'] = df.loc[i - 1, 'Kisa_Sinyal_Fiyati']

                else:
                    kisa_egim_asagi = (ema21 < df.loc[i - 1, 'EMA21'] and ema13 < df.loc[i - 1, 'EMA13'])

                    if kapanis < ema21 and kisa_egim_asagi:
                        df.loc[i, 'Kisa_Durum'] = "SAT"
                        if kisa_durum_once != "SAT":
                            df.loc[i, 'Kisa_Bar_Sayaci'] = 1
                            df.loc[i, 'Kisa_Sinyal_Tarihi'] = df.loc[i, 'Tarih']
                            df.loc[i, 'Kisa_Sinyal_Fiyati'] = df.loc[i, 'Kapanış']
                        else:
                            df.loc[i, 'Kisa_Bar_Sayaci'] = df.loc[i - 1, 'Kisa_Bar_Sayaci'] + 1
                            df.loc[i, 'Kisa_Sinyal_Tarihi'] = df.loc[i - 1, 'Kisa_Sinyal_Tarihi']
                            df.loc[i, 'Kisa_Sinyal_Fiyati'] = df.loc[i - 1, 'Kisa_Sinyal_Fiyati']
                    else:
                        # AL sinyalini koruma mantığı
                        if kisa_durum_once == 'AL' and df.loc[i, 'Kisa_Durum'] == 'BEKLE':
                            df.loc[i, 'Kisa_Durum'] = "AL"
                            df.loc[i, 'Kisa_Bar_Sayaci'] = df.loc[i - 1, 'Kisa_Bar_Sayaci'] + 1
                            df.loc[i, 'Kisa_Sinyal_Tarihi'] = df.loc[i - 1, 'Kisa_Sinyal_Tarihi']
                            df.loc[i, 'Kisa_Sinyal_Fiyati'] = df.loc[i - 1, 'Kisa_Sinyal_Fiyati']
                        else:
                            df.loc[i, 'Kisa_Durum'] = "BEKLE"
                            df.loc[i, 'Kisa_Bar_Sayaci'] = 0
                            df.loc[i, 'Kisa_Sinyal_Tarihi'] = pd.NaT
                            df.loc[i, 'Kisa_Sinyal_Fiyati'] = pd.NA

            # ORTA VADE SİNYALLERİ
            if all(col in df.columns for col in ['EMA34', 'EMA55']) and all(
                    pd.notna(df.loc[i, col]) for col in ['EMA34', 'EMA55']):

                ema34 = df.loc[i, 'EMA34']
                ema55 = df.loc[i, 'EMA55']

                if kapanis > ema34 and kapanis > ema55 and ema34 > ema55:
                    df.loc[i, 'Orta_Durum'] = "AL"
                    if orta_durum_once != "AL":
                        df.loc[i, 'Orta_Bar_Sayaci'] = 1
                        df.loc[i, 'Orta_Sinyal_Tarihi'] = df.loc[i, 'Tarih']
                        df.loc[i, 'Orta_Sinyal_Fiyati'] = df.loc[i, 'Kapanış']
                    else:
                        df.loc[i, 'Orta_Bar_Sayaci'] = df.loc[i - 1, 'Orta_Bar_Sayaci'] + 1
                        df.loc[i, 'Orta_Sinyal_Tarihi'] = df.loc[i - 1, 'Orta_Sinyal_Tarihi']
                        df.loc[i, 'Orta_Sinyal_Fiyati'] = df.loc[i - 1, 'Orta_Sinyal_Fiyati']

                elif kapanis < ema55:
                    df.loc[i, 'Orta_Durum'] = "SAT"
                    if orta_durum_once != "SAT":
                        df.loc[i, 'Orta_Bar_Sayaci'] = 1
                        df.loc[i, 'Orta_Sinyal_Tarihi'] = df.loc[i, 'Tarih']
                        df.loc[i, 'Orta_Sinyal_Fiyati'] = df.loc[i, 'Kapanış']
                    else:
                        df.loc[i, 'Orta_Bar_Sayaci'] = df.loc[i - 1, 'Orta_Bar_Sayaci'] + 1
                        df.loc[i, 'Orta_Sinyal_Tarihi'] = df.loc[i - 1, 'Orta_Sinyal_Tarihi']
                        df.loc[i, 'Orta_Sinyal_Fiyati'] = df.loc[i - 1, 'Orta_Sinyal_Fiyati']

                else:
                    df.loc[i, 'Orta_Durum'] = "BEKLE"
                    df.loc[i, 'Orta_Bar_Sayaci'] = 0
                    df.loc[i, 'Orta_Sinyal_Tarihi'] = pd.NaT
                    df.loc[i, 'Orta_Sinyal_Fiyati'] = pd.NA

            # UZUN VADE SİNYALLERİ
            if all(col in df.columns for col in ['EMA89', 'EMA144']) and all(
                    pd.notna(df.loc[i, col]) for col in ['EMA89', 'EMA144']):
                ema89 = df.loc[i, 'EMA89']
                ema144 = df.loc[i, 'EMA144']

                if kapanis > ema89 and kapanis > ema144:
                    df.loc[i, 'Uzun_Durum'] = "AL"
                    if uzun_durum_once != "AL":
                        df.loc[i, 'Uzun_Bar_Sayaci'] = 1
                        df.loc[i, 'Uzun_Sinyal_Tarihi'] = df.loc[i, 'Tarih']
                        df.loc[i, 'Uzun_Sinyal_Fiyati'] = df.loc[i, 'Kapanış']
                    else:
                        df.loc[i, 'Uzun_Bar_Sayaci'] = df.loc[i - 1, 'Uzun_Bar_Sayaci'] + 1
                        df.loc[i, 'Uzun_Sinyal_Tarihi'] = df.loc[i - 1, 'Uzun_Sinyal_Tarihi']
                        df.loc[i, 'Uzun_Sinyal_Fiyati'] = df.loc[i - 1, 'Uzun_Sinyal_Fiyati']

                elif kapanis < ema144:
                    df.loc[i, 'Uzun_Durum'] = "SAT"
                    if uzun_durum_once != "SAT":
                        df.loc[i, 'Uzun_Bar_Sayaci'] = 1
                        df.loc[i, 'Uzun_Sinyal_Tarihi'] = df.loc[i, 'Tarih']
                        df.loc[i, 'Uzun_Sinyal_Fiyati'] = df.loc[i, 'Kapanış']
                    else:
                        df.loc[i, 'Uzun_Bar_Sayaci'] = df.loc[i - 1, 'Uzun_Bar_Sayaci'] + 1
                        df.loc[i, 'Uzun_Sinyal_Tarihi'] = df.loc[i - 1, 'Uzun_Sinyal_Tarihi']
                        df.loc[i, 'Uzun_Sinyal_Fiyati'] = df.loc[i - 1, 'Uzun_Sinyal_Fiyati']

                else:
                    df.loc[i, 'Uzun_Durum'] = "BEKLE"
                    df.loc[i, 'Uzun_Bar_Sayaci'] = 0
                    df.loc[i, 'Uzun_Sinyal_Tarihi'] = pd.NaT
                    df.loc[i, 'Uzun_Sinyal_Fiyati'] = pd.NA

            # SİNYAL BOZULMA UYARILARINI KONTROL ET
            warnings_dict = self.check_signal_deterioration(df, i)
            df.loc[i, 'Kisa_Uyari'] = warnings_dict['kisa_uyari']
            df.loc[i, 'Orta_Uyari'] = warnings_dict['orta_uyari']
            df.loc[i, 'Uzun_Uyari'] = warnings_dict['uzun_uyari']

        return df

    @staticmethod
    def get_latest_signals(df: pd.DataFrame) -> Optional[Dict[str, Any]]:
        """En son sinyal durumlarını getir"""
        if len(df) == 0:
            return None

        latest = df.iloc[-1]

        # Sinyal gücü ataması
        kisa_guc = '⭐' if latest['Kisa_Durum'] != 'BEKLE' else '⏳'
        orta_guc = '⭐' if latest['Orta_Durum'] != 'BEKLE' else '⏳'
        uzun_guc = '⭐' if latest['Uzun_Durum'] != 'BEKLE' else '⏳'

        # Fiyat farkı hesaplamaları
        kisa_fark_tl = latest['Kapanış'] - latest['Kisa_Sinyal_Fiyati'] if pd.notna(
            latest['Kisa_Sinyal_Fiyati']) else pd.NA
        kisa_fark_yuzde = (kisa_fark_tl / latest['Kisa_Sinyal_Fiyati']) * 100 if pd.notna(kisa_fark_tl) else pd.NA

        orta_fark_tl = latest['Kapanış'] - latest['Orta_Sinyal_Fiyati'] if pd.notna(
            latest['Orta_Sinyal_Fiyati']) else pd.NA
        orta_fark_yuzde = (orta_fark_tl / latest['Orta_Sinyal_Fiyati']) * 100 if pd.notna(orta_fark_tl) else pd.NA

        uzun_fark_tl = latest['Kapanış'] - latest['Uzun_Sinyal_Fiyati'] if pd.notna(
            latest['Uzun_Sinyal_Fiyati']) else pd.NA
        uzun_fark_yuzde = (uzun_fark_tl / latest['Uzun_Sinyal_Fiyati']) * 100 if pd.notna(uzun_fark_tl) else pd.NA

        # NaN değerler yerine 'Yok' metnini kullanma
        def format_value(value, format_str, default='Yok'):
            if pd.notna(value):
                return format_str.format(value)
            return default

        return {
            'tarih': latest['Tarih'].strftime('%Y-%m-%d'),
            'kapanis': latest['Kapanış'],
            'kisa': {
                'durum': latest['Kisa_Durum'],
                'bar_sayaci': latest['Kisa_Bar_Sayaci'],
                'sinyal_tarihi': format_value(latest['Kisa_Sinyal_Tarihi'], '{:%d.%m.%Y}'),
                'sinyal_fiyati': format_value(latest['Kisa_Sinyal_Fiyati'], '{:.2f}'),
                'fark_tl': format_value(kisa_fark_tl, '{:.2f}'),
                'fark_yuzde': format_value(kisa_fark_yuzde, '{:.2f}%'),
                'guc': kisa_guc,
                'uyari': latest['Kisa_Uyari'] if 'Kisa_Uyari' in df.columns else ''
            },
            'orta': {
                'durum': latest['Orta_Durum'],
                'bar_sayaci': latest['Orta_Bar_Sayaci'],
                'sinyal_tarihi': format_value(latest['Orta_Sinyal_Tarihi'], '{:%d.%m.%Y}'),
                'sinyal_fiyati': format_value(latest['Orta_Sinyal_Fiyati'], '{:.2f}'),
                'fark_tl': format_value(orta_fark_tl, '{:.2f}'),
                'fark_yuzde': format_value(orta_fark_yuzde, '{:.2f}%'),
                'guc': orta_guc,
                'uyari': latest['Orta_Uyari'] if 'Orta_Uyari' in df.columns else ''
            },
            'uzun': {
                'durum': latest['Uzun_Durum'],
                'bar_sayaci': latest['Uzun_Bar_Sayaci'],
                'sinyal_tarihi': format_value(latest['Uzun_Sinyal_Tarihi'], '{:%d.%m.%Y}'),
                'sinyal_fiyati': format_value(latest['Uzun_Sinyal_Fiyati'], '{:.2f}'),
                'fark_tl': format_value(uzun_fark_tl, '{:.2f}'),
                'fark_yuzde': format_value(uzun_fark_yuzde, '{:.2f}%'),
                'guc': uzun_guc,
                'uyari': latest['Uzun_Uyari'] if 'Uzun_Uyari' in df.columns else ''
            }
        }

    def process_single_stock(self, file_path: str) -> Optional[Dict[str, Any]]:
        """Tek bir hisse için EMA analizi yap ve sonuçları topla"""
        ticker_name = os.path.splitext(os.path.basename(file_path))[0]
        print(f"{Fore.YELLOW} EMA sinyalleri hesaplanıyor: {ticker_name}...")

        try:
            df = self.load_stock_data(file_path)

            # En az kısa vade EMA için yeterli veri yoksa hata ver
            if df.empty or len(df) < min(self.ema_periods['kisa_vade']):
                raise ValueError("Yeterli veri yok veya dosya geçersiz.")

            # Tüm EMA'ları ve sinyalleri hesapla
            df = self.calculate_all_emas(df)
            df = self.determine_signal_status(df)

            latest_signals = self.get_latest_signals(df)

            if latest_signals:
                self.successful_files.append(ticker_name)
                latest_signals['hisse'] = ticker_name
                print(f"{Fore.GREEN}✅ {ticker_name} için analiz başarılı.")
            else:
                self.failed_files.append(ticker_name)
                print(f"{Fore.RED}❌ {ticker_name} için sinyal oluşturulamadı.")

            return latest_signals

        except (ValueError, pd.errors.ParserError) as e:
            print(f"{Fore.RED}❌ {ticker_name} için hata: {e}")
            self.failed_files.append(ticker_name)
            return None

    def main(self):
        """Ana fonksiyon"""
        print(f"{Fore.CYAN} BorsaPin EMA Analiz Sistemi Başlatılıyor...")

        input_folder = "StokData/Kapanis/"
        input_files = glob.glob(os.path.join(input_folder, "*.xlsx"))

        if not input_files:
            print(f"{Fore.RED}❌ {input_folder} klasöründe Excel dosyası bulunamadı!")
            return

        all_latest_results: List[Dict[str, Any]] = []
        for i, file_path in enumerate(input_files, 1):
            print(f"\n{Fore.MAGENTA}[{i}/{len(input_files)}] İşleniyor...")
            latest_signals = self.process_single_stock(file_path)
            if latest_signals:
                all_latest_results.append(latest_signals)

        if all_latest_results:
            self.save_all_signals_to_excel(all_latest_results)

        self.print_summary()
        self.save_failed_list()

        print(f"\n{Fore.GREEN} EMA analiz işlemi tamamlandı!")

    def save_all_signals_to_excel(self, results: List[Dict[str, Any]]):
        """Tüm sinyalleri tek bir Excel dosyasına farklı sayfalarda kaydet"""
        output_folder = "StokData/"
        os.makedirs(output_folder, exist_ok=True)
        filename = os.path.join(output_folder, "BorsaPin_EMA_Analizleri.xlsx")

        summary_df = self.create_summary_table(results)
        strong_signals_df = self.filter_strong_signals_df(summary_df)
        warning_signals_df = self.filter_warning_signals_df(summary_df)

        # Detaylı sinyal tabloları oluştur
        kisa_vade_df = self.create_detailed_signal_table(results, 'kisa')
        orta_vade_df = self.create_detailed_signal_table(results, 'orta')
        uzun_vade_df = self.create_detailed_signal_table(results, 'uzun')

        # İstatistik tabloları oluştur
        statistics_df = self.create_statistics_table(results)

        with pd.ExcelWriter(filename, engine='openpyxl') as writer:
            # Ana özet sayfası
            if not summary_df.empty:
                summary_df.to_excel(writer, sheet_name='Genel Özet', index=False)
                self.format_worksheet(writer.sheets['Genel Özet'], summary_df)

            # Güçlü sinyaller sayfası
            if not strong_signals_df.empty:
                strong_signals_df.to_excel(writer, sheet_name='Güçlü Sinyaller', index=False)
                self.format_worksheet(writer.sheets['Güçlü Sinyaller'], strong_signals_df)

            # Uyarı sinyalleri sayfası
            if not warning_signals_df.empty:
                warning_signals_df.to_excel(writer, sheet_name='Uyarı Sinyalleri', index=False)
                self.format_worksheet(writer.sheets['Uyarı Sinyalleri'], warning_signals_df)

            # Detaylı vade sayfaları
            if not kisa_vade_df.empty:
                kisa_vade_df.to_excel(writer, sheet_name='Kısa Vade Detay', index=False)
                self.format_worksheet(writer.sheets['Kısa Vade Detay'], kisa_vade_df)

            if not orta_vade_df.empty:
                orta_vade_df.to_excel(writer, sheet_name='Orta Vade Detay', index=False)
                self.format_worksheet(writer.sheets['Orta Vade Detay'], orta_vade_df)

            if not uzun_vade_df.empty:
                uzun_vade_df.to_excel(writer, sheet_name='Uzun Vade Detay', index=False)
                self.format_worksheet(writer.sheets['Uzun Vade Detay'], uzun_vade_df)

            # İstatistik sayfası
            if not statistics_df.empty:
                statistics_df.to_excel(writer, sheet_name='İstatistikler', index=False)
                self.format_worksheet(writer.sheets['İstatistikler'], statistics_df)

        print(f"{Fore.GREEN}✅ Tüm analiz sonuçları başarıyla kaydedildi: {filename}")

    @staticmethod
    def create_summary_table(results: List[Dict[str, Any]]) -> pd.DataFrame:
        """Özet Tablolar """
        summary_data = [
            {
                'Hisse': res['hisse'],
                'Kapanış': round(res['kapanis'], 2),
                'Kısa Vade': res['kisa']['durum'],
                'Kısa Uyarı': res['kisa']['uyari'],
                'Sinyal Süresi': res['kisa']['bar_sayaci'],
                'Kısa Vade Sinyal Tarihi': res['kisa']['sinyal_tarihi'],
                'Kısa Vade Sinyal Fiyatı': res['kisa']['sinyal_fiyati'],
                'Kısa Vade Kazanç TL': res['kisa']['fark_tl'],
                'Kısa Vade Kazanç %': res['kisa']['fark_yuzde'],
                'Orta Vade': res['orta']['durum'],
                'Orta Uyarı': res['orta']['uyari'],
                'Orta Sinyal Süresi': res['orta']['bar_sayaci'],
                'Orta Vade Sinyal Tarihi': res['orta']['sinyal_tarihi'],
                'Orta Vade Sinyal Fiyatı': res['orta']['sinyal_fiyati'],
                'Orta Vade Kazanç TL': res['orta']['fark_tl'],
                'Orta Vade Kazanç %': res['orta']['fark_yuzde'],
                'Uzun Vade': res['uzun']['durum'],
                'Uzun Uyarı': res['uzun']['uyari'],
                'Uzun Sinyal Süresi': res['uzun']['bar_sayaci'],
                'Uzun Vade Sinyal Tarihi': res['uzun']['sinyal_tarihi'],
                'Uzun Vade Sinyal Fiyatı': res['uzun']['sinyal_fiyati'],
                'Uzun Vade Kazanç TL': res['uzun']['fark_tl'],
                'Uzun Vade Kazanç %': res['uzun']['fark_yuzde']
            } for res in results
        ]
        return pd.DataFrame(summary_data)

    @staticmethod
    def create_detailed_signal_table(results: List[Dict[str, Any]], vade_type: str) -> pd.DataFrame:
        """Belirli vade için detaylı sinyal tablosu oluştur"""
        detailed_data = []
        for res in results:
            vade_data = res[vade_type]
            if vade_data['durum'] != 'BEKLE':
                detailed_data.append({
                    'Hisse': res['hisse'],
                    'Kapanış': round(res['kapanis'], 2),
                    'Sinyal Durumu': vade_data['durum'],
                    'Uyarı Durumu': vade_data['uyari'],
                    'Sinyal Süresi (Gün)': vade_data['bar_sayaci'],
                    'Sinyal Tarihi': vade_data['sinyal_tarihi'],
                    'Sinyal Fiyatı': vade_data['sinyal_fiyati'],
                    'Kazanç/Kayıp TL': vade_data['fark_tl'],
                    'Kazanç/Kayıp %': vade_data['fark_yuzde']
                })

        df = pd.DataFrame(detailed_data)
        if not df.empty:
            # Sinyal süresine göre sırala (en uzun süreli sinyaller önce)
            df = df.sort_values('Sinyal Süresi (Gün)', ascending=False).reset_index(drop=True)

        return df

    @staticmethod
    def filter_warning_signals_df(summary_df: pd.DataFrame) -> pd.DataFrame:
        """Uyarı sinyali olan hisseleri filtreleme"""
        if summary_df.empty:
            return pd.DataFrame()

        warning_signals_df = summary_df[
            (summary_df['Kısa Uyarı'] != '') |
            (summary_df['Orta Uyarı'] != '') |
            (summary_df['Uzun Uyarı'] != '')
            ].reset_index(drop=True)

        return warning_signals_df

    @staticmethod
    def create_statistics_table(results: List[Dict[str, Any]]) -> pd.DataFrame:
        """İstatistik tablosu"""
        stats_data = []

        # Genel istatistikler
        total_stocks = len(results)

        # Her vade için istatistikler
        for vade_key, vade_name in [('kisa', 'Kısa Vade'), ('orta', 'Orta Vade'), ('uzun', 'Uzun Vade')]:
            al_sinyali = sum(1 for res in results if res[vade_key]['durum'] == 'AL')
            sat_sinyali = sum(1 for res in results if res[vade_key]['durum'] == 'SAT')
            bekle_sinyali = sum(1 for res in results if res[vade_key]['durum'] == 'BEKLE')
            uyari_sinyali = sum(1 for res in results if res[vade_key]['uyari'] != '')

            # Ortalama sinyal süresi (sadece aktif sinyaller için)
            aktif_sinyaller = [res[vade_key]['bar_sayaci'] for res in results
                               if res[vade_key]['durum'] != 'BEKLE' and res[vade_key]['bar_sayaci'] > 0]
            ortalama_sure = round(sum(aktif_sinyaller) / len(aktif_sinyaller), 1) if aktif_sinyaller else 0

            # En uzun sinyal süresi
            max_sure = max(aktif_sinyaller) if aktif_sinyaller else 0

            # Pozitif/negatif performans (sadece AL sinyalleri için)
            al_sinyalleri = [res for res in results if res[vade_key]['durum'] == 'AL']
            pozitif_performans = 0
            negatif_performans = 0

            for res in al_sinyalleri:
                try:
                    fark_str = res[vade_key]['fark_yuzde']
                    if fark_str != 'Yok' and '%' in fark_str:
                        fark_value = float(fark_str.replace('%', ''))
                        if fark_value > 0:
                            pozitif_performans += 1
                        else:
                            negatif_performans += 1
                except ValueError:
                    pass

            stats_data.extend([
                {
                    'Vade Türü': vade_name,
                    'Metrik': 'Toplam Hisse Sayısı',
                    'Değer': total_stocks,
                    'Oran %': '100.0'
                },
                {
                    'Vade Türü': vade_name,
                    'Metrik': 'AL Sinyali',
                    'Değer': al_sinyali,
                    'Oran %': f"{(al_sinyali / total_stocks * 100):.1f}" if total_stocks > 0 else "0.0"
                },
                {
                    'Vade Türü': vade_name,
                    'Metrik': 'SAT Sinyali',
                    'Değer': sat_sinyali,
                    'Oran %': f"{(sat_sinyali / total_stocks * 100):.1f}" if total_stocks > 0 else "0.0"
                },
                {
                    'Vade Türü': vade_name,
                    'Metrik': 'BEKLE Durumu',
                    'Değer': bekle_sinyali,
                    'Oran %': f"{(bekle_sinyali / total_stocks * 100):.1f}" if total_stocks > 0 else "0.0"
                },
                {
                    'Vade Türü': vade_name,
                    'Metrik': 'Uyarı Sinyali',
                    'Değer': uyari_sinyali,
                    'Oran %': f"{(uyari_sinyali / total_stocks * 100):.1f}" if total_stocks > 0 else "0.0"
                },
                {
                    'Vade Türü': vade_name,
                    'Metrik': 'Ortalama Sinyal Süresi (Gün)',
                    'Değer': ortalama_sure,
                    'Oran %': '-'
                },
                {
                    'Vade Türü': vade_name,
                    'Metrik': 'En Uzun Sinyal Süresi (Gün)',
                    'Değer': max_sure,
                    'Oran %': '-'
                },
                {
                    'Vade Türü': vade_name,
                    'Metrik': 'Pozitif Performans (AL)',
                    'Değer': pozitif_performans,
                    'Oran %': f"{(pozitif_performans / al_sinyali * 100):.1f}" if al_sinyali > 0 else "0.0"
                },
                {
                    'Vade Türü': vade_name,
                    'Metrik': 'Negatif Performans (AL)',
                    'Değer': negatif_performans,
                    'Oran %': f"{(negatif_performans / al_sinyali * 100):.1f}" if al_sinyali > 0 else "0.0"
                }
            ])

        # Güçlü sinyaller (tüm vadeler AL)
        guclu_sinyaller = sum(1 for res in results
                              if res['kisa']['durum'] == 'AL' and
                              res['orta']['durum'] == 'AL' and
                              res['uzun']['durum'] == 'AL')

        # Toplam uyarı sinyalleri
        toplam_uyari = sum(1 for res in results
                           if res['kisa']['uyari'] != '' or
                           res['orta']['uyari'] != '' or
                           res['uzun']['uyari'] != '')

        stats_data.extend([
            {
                'Vade Türü': 'Genel',
                'Metrik': 'Güçlü Sinyal (Tüm Vadeler AL)',
                'Değer': guclu_sinyaller,
                'Oran %': f"{(guclu_sinyaller / total_stocks * 100):.1f}" if total_stocks > 0 else "0.0"
            },
            {
                'Vade Türü': 'Genel',
                'Metrik': 'Toplam Uyarı Sinyali',
                'Değer': toplam_uyari,
                'Oran %': f"{(toplam_uyari / total_stocks * 100):.1f}" if total_stocks > 0 else "0.0"
            }
        ])

        return pd.DataFrame(stats_data)

    @staticmethod
    def format_worksheet(worksheet, df):
        """Excel çalışma sayfası formatları """
        try:
            # Başlık satırı formatı
            header_fill = PatternFill(start_color='366092', end_color='366092', fill_type='solid')
            header_font = Font(color='FFFFFF', bold=True)
            header_alignment = Alignment(horizontal='center', vertical='center')

            # Kenarlık stili
            thin_border = Border(
                left=Side(style='thin'),
                right=Side(style='thin'),
                top=Side(style='thin'),
                bottom=Side(style='thin')
            )

            # Başlık satırını formatla
            for col_num, column_title in enumerate(df.columns, 1):
                cell = worksheet.cell(row=1, column=col_num)
                cell.fill = header_fill
                cell.font = header_font
                cell.alignment = header_alignment
                cell.border = thin_border

            # Veri satırlarını formatla
            for row_num in range(2, len(df) + 2):
                for col_num in range(1, len(df.columns) + 1):
                    cell = worksheet.cell(row=row_num, column=col_num)
                    cell.border = thin_border
                    cell.alignment = Alignment(horizontal='center', vertical='center')

            # Sütun genişliklerini ayarla
            for column in worksheet.columns:
                max_length = 0
                column_letter = column[0].column_letter

                for cell in column:
                    try:
                        if len(str(cell.value)) > max_length:
                            max_length = len(str(cell.value))
                    except (TypeError, ValueError):
                        pass

                adjusted_width = min(max_length + 2, 20)
                worksheet.column_dimensions[column_letter].width = adjusted_width

            # Freeze panes ve autofilter
            worksheet.freeze_panes = 'A2'
            worksheet.auto_filter.ref = worksheet.dimensions

            # Sinyal durumu sütunları için renk kodlaması
            for row_num in range(2, len(df) + 2):
                for col_num, column_name in enumerate(df.columns, 1):
                    cell = worksheet.cell(row=row_num, column=col_num)

                    # Ana özet sayfaları için vade sütunları
                    if 'Vade' in column_name and column_name.endswith('Vade'):
                        if cell.value == 'AL':
                            cell.fill = PatternFill(start_color='90EE90', end_color='90EE90', fill_type='solid')
                            cell.font = Font(bold=True, color='006400')
                        elif cell.value == 'SAT':
                            cell.fill = PatternFill(start_color='FFB6C1', end_color='FFB6C1', fill_type='solid')
                            cell.font = Font(bold=True, color='8B0000')
                        elif cell.value == 'BEKLE':
                            cell.fill = PatternFill(start_color='FFFFE0', end_color='FFFFE0', fill_type='solid')
                            cell.font = Font(bold=True, color='B8860B')

                    # Detay sayfaları için "Sinyal Durumu" sütunu
                    elif column_name == 'Sinyal Durumu':
                        if cell.value == 'AL':
                            cell.fill = PatternFill(start_color='90EE90', end_color='90EE90', fill_type='solid')
                            cell.font = Font(bold=True, color='006400')
                        elif cell.value == 'SAT':
                            cell.fill = PatternFill(start_color='FFB6C1', end_color='FFB6C1', fill_type='solid')
                            cell.font = Font(bold=True, color='8B0000')

                    # Uyarı sütunları için renk kodlaması
                    elif 'Uyarı' in column_name:
                        if cell.value and cell.value != '':
                            cell.fill = PatternFill(start_color='FFA500', end_color='FFA500', fill_type='solid')
                            cell.font = Font(bold=True, color='FFFFFF')

                    # Uyarı durumu sütunu için renk kodlaması
                    elif column_name == 'Uyarı Durumu':
                        if cell.value and cell.value != '':
                            cell.fill = PatternFill(start_color='FFA500', end_color='FFA500', fill_type='solid')
                            cell.font = Font(bold=True, color='FFFFFF')

                    # Kazanç/Kayıp yüzde değerleri için renk kodlaması
                    elif 'Kazanç' in column_name and '%' in column_name:
                        try:
                            if cell.value and cell.value != 'Yok' and '%' in str(cell.value):
                                percentage_value = float(str(cell.value).replace('%', ''))
                                if percentage_value > 0:
                                    cell.fill = PatternFill(start_color='E6FFE6', end_color='E6FFE6', fill_type='solid')
                                    cell.font = Font(color='006400', bold=True)
                                elif percentage_value < 0:
                                    cell.fill = PatternFill(start_color='FFE6E6', end_color='FFE6E6', fill_type='solid')
                                    cell.font = Font(color='8B0000', bold=True)
                        except (ValueError, TypeError):
                            pass

                    # Kazanç/Kayıp TL değerleri için renk kodlaması
                    elif 'Kazanç' in column_name and 'TL' in column_name:
                        try:
                            if cell.value and cell.value != 'Yok':
                                tl_value = float(str(cell.value))
                                if tl_value > 0:
                                    cell.fill = PatternFill(start_color='E6FFE6', end_color='E6FFE6', fill_type='solid')
                                    cell.font = Font(color='006400', bold=True)
                                elif tl_value < 0:
                                    cell.fill = PatternFill(start_color='FFE6E6', end_color='FFE6E6', fill_type='solid')
                                    cell.font = Font(color='8B0000', bold=True)
                        except (ValueError, TypeError):
                            pass

                    # Sinyal süresi için renk gradyanı (uzun süreli sinyaller daha koyu)
                    elif 'Sinyal Süresi' in column_name or 'Sinyal Süresi (Gün)' in column_name:
                        try:
                            if cell.value and isinstance(cell.value, (int, float)) and cell.value > 0:
                                days = int(cell.value)
                                if days >= 30:
                                    cell.fill = PatternFill(start_color='4CAF50', end_color='4CAF50', fill_type='solid')
                                    cell.font = Font(color='FFFFFF', bold=True)
                                elif days >= 14:
                                    cell.fill = PatternFill(start_color='8BC34A', end_color='8BC34A', fill_type='solid')
                                    cell.font = Font(color='FFFFFF', bold=True)
                                elif days >= 7:
                                    cell.fill = PatternFill(start_color='CDDC39', end_color='CDDC39', fill_type='solid')
                                    cell.font = Font(color='333333', bold=True)
                                elif days >= 3:
                                    cell.fill = PatternFill(start_color='FFF176', end_color='FFF176', fill_type='solid')
                                    cell.font = Font(color='333333', bold=True)
                        except (ValueError, TypeError):
                            pass
        except Exception as e:
            print(f"{Fore.RED}❌ Excel formatlama hatası: {e}")

    @staticmethod
    def filter_strong_signals_df(summary_df: pd.DataFrame) -> pd.DataFrame:
        """Tüm vadelerde 'AL' sinyali olan hisseleri filtrele"""
        if summary_df.empty:
            return pd.DataFrame()
        strong_signals_df = summary_df[
            (summary_df['Kısa Vade'] == 'AL') &
            (summary_df['Orta Vade'] == 'AL') &
            (summary_df['Uzun Vade'] == 'AL')
            ].reset_index(drop=True)
        return strong_signals_df

    def print_summary(self):
        """İşlem özetini ekrana yazdır"""
        total_files = len(self.successful_files) + len(self.failed_files)
        print("\n" + "=" * 40)
        print(f"{Fore.CYAN}BorsaPin EMA Analizi Özeti")
        print("=" * 40)
        print(f"{Fore.GREEN}✅ Başarılı Analiz Edilen Hisse Sayısı: {len(self.successful_files)} / {total_files}")
        if self.successful_files:
            print(f"{Fore.GREEN}  - Hisse Listesi: {', '.join(self.successful_files)}")
        print(f"{Fore.RED}❌ Hata Alan Hisse Sayısı: {len(self.failed_files)} / {total_files}")
        if self.failed_files:
            print(f"{Fore.RED}  - Hisse Listesi: {', '.join(self.failed_files)}")
        print("=" * 40)

    def save_failed_list(self):
        """Hata veren hisseleri bir dosyaya kaydet"""
        if self.failed_files:
            with open("StokData/hata_veren_hisseler.txt", "w") as f:
                f.write("\n".join(self.failed_files))
            print(f"{Fore.RED}❌ Hata veren hisse listesi 'StokData/hata_veren_hisseler.txt' dosyasına kaydedildi.")


if __name__ == "__main__":
    analyzer = BorsaPinEMAAnalyzer()
    analyzer.main()

 

Kod gösterimleri ile ilgili sıkıntı

11 Ağustos 2025 BorsaPin, Code is prority, İndikatör, Pine Script, Python, Teknik Analiz



Paylaştığım kodlarda sıkıntı yaşarsanız Google Drive Alanından indirmeniz daha iyi olur. Sitedeki kod gösterici eklentide ufak bir problem vardı. Bu sorunu başka bir plugingle çözdüm ve yazıların bir çoğunu güncelledim ama gözden kaçan düzenlenmemiş Python betiği yada Trading View Pine Script kodlarında sıkıntı olabilir.
Eğer sorun yaşarsanız yazının altına yorum yazarsanız tekrar gözden geçiririm. 


Borsapin Python Bist Tarama  ve Trading View Pine Script İndikatörleri için Google Drive alanı için buraya tıklayabilirsiniz.

 

Borsapin EMA Sinyal Tablosu (Kısa, Orta, Uzun Vade)

10 Ağustos 2025 BorsaPin, Teknik Analiz, Trading Viewal sat sinyali, algoritmik trading, aylık analiz, backtesting, borsa eğitimi, borsa sinyali, BorsaPin, çoklu varlık analizi, çoklu zaman dilimi analizi, day trading, destek direnç, ema crossover, fibonacci ema, fibonacci sayıları, grafik analizi, günlük analiz, hacim analizi, haftalık analiz, hisse senedi analizi, kısa vade sinyali, kripto para analizi, momentum indikatörü, orta vade sinyali, otomatik sinyal, performans analizi, Pine Script, piyasa analizi, piyasa momentumu, portföy yönetimi, pozisyon trading, quantitative analysis, risk yönetimi, sinyal tablosu, Stop-Loss, swing trading, Teknik Analiz, teknik indikatör, trading stratejisi, tradingview indikatörü, tradingview kodu, trend analizi, trend takibi, Üstel Hareketli Ortalama, uzun vade sinyali, volatilite analizi, yatırım stratejisi

Teknik analizde hareketli ortalamalar, piyasanın genel trendini ve momentum değişimlerini anlamak için kullanılan en temel araçlardan biridir.
Borsapin EMA Sinyal Tablosu, Fibonacci sayı dizisine dayalı EMA (Üstel Hareketli Ortalama) sistemini kullanarak yatırımcılara üç farklı zaman diliminde (kısa, orta, uzun vade) sinyal üreten gelişmiş bir indikatördür.

Fibonacci EMA Serileri
Kısa Vade EMA’lar: 5, 8, 13, 21

En hızlı tepki veren ortalamalar, Günlük işlemler için ideal , Kısa vadeli trend değişimlerini yakalar

Orta Vade EMA’lar: 34, 55

Orta vadeli trendin yönünü belirler, Haftalık strateji geliştiriciler için uygun, Gürültüyü filtreler, daha güvenilir sinyaller üretir

Uzun Vade EMA’lar: 89, 144

Ana trendin yönünü gösterir, Uzun vadeli yatırım kararları için kritik, En az yanıltıcı sinyaller üretir

Kısa Vade Sinyal Sistemi Mantığı

AL Sinyali Başlangıcı: Fiyat tüm EMA’ların (5,8,13,21) üzerinde ve EMA’ların eğimi yukarı yönlü
Sinyal Devamı: EMA 21’in altına geçici sarkmalarda bile, EMA eğimi yukarı yönlü kaldığı sürece AL sinyali bozulmaz
SAT Sinyali: Fiyat EMA 21’in altında ve EMA eğimi aşağı yönlü ise

Orta ve Uzun Vade Sistemlerin Mantığı

AL Sinyali: Fiyat ilgili EMA’ların üzerinde
SAT Sinyali: Fiyat kritik EMA seviyesinin altında (55 ve 89)

Aynı anda üç farklı perspektiften piyasayı değerlendirebilirsiniz. Kısa vadeli gürültüyü uzun vadeli trendden ayırabilirsiniz. Sinyal çakışmalarında güçlü fırsatları belirleyebilirsiniz.

Bar sayacı ile sinyalin ne kadar süredir aktif olduğunu görebilir, Güç göstergesi (⭐) ile sinyalin kalitesini değerlendirme yapabilirsiniz,

Avantajları 
Farklı zaman dilimlerinde çelişkili sinyallerde temkinli olmanızı sağlar. Kısa vade sinyaller ile  giriş/çıkış noktalarını,  Orta-uzun vade sinyalleri ile ana trend yönünün teyidi, Sinyal tarihlerini takip ederek performans analizi yapabilirsiniz. Farklı hisseler için aynı kriterlerde karşılaştırma yapabilir, ayrıca sektörel rotasyonda hangi hisselerin güçlü olduğunu belirleme şansına sahip olabilirsiniz. Varlıklara sistematik yaklaşıp, duygusal karar almanızı engeller. Size Objektif sinyal üretimlerini gösterir.

Dezavantajları ve Riskleri
EMA’lar geçmiş verilerle hesaplandığı için sinyaller gecikmeli gelir, Hızlı piyasa hareketlerinde geç kalabilir. Trend dönüş noktalarında yanıltıcı sinyaller verebilir. Yatay seyreden piyasalarda çok fazla sinyal üretebilir. Whipsaw (sahte sinyal) riski yüksek. Kısa vadede sık giriş-çıkış maliyetleri artabilir. Piyasa sadece teknik faktörlerden etkilenmez. Haberlere, makro ekonomik değişimlere tepki verebilir. Hacim, volatilite gibi faktörleri  indikatör hesaplamıyor. Geçmiş verilerle mükemmel çalışan parametreler gelecekte başarısız olabilir. Mesala Fibonacci sayıları her piyasa için optimal olmayabilir. Farklı volatilite ortamlarında farklı sonuçlar verebilir

Uyarılar 

Diğer teknik indikatörlerle teyit edin. Hacim analizini ihmal etmeyin, Para Giriş çıkışlarını kontrol edin, Temel analiz ile destekleyin. Yüksek Volatilite Dönemlerinde Özellikle dikkat etmeniz önerilir.  Borsapin EMA Sinyal Tablosu, Fibonacci sayı dizisinin doğal uyumunu teknik analize taşıyan, çoklu zaman diliminde objektif sinyaller üreten güçlü bir araçtır. Doğru kullanıldığında yatırımcılara önemli avantajlar sağlarken, limitasyonlarının da farkında olunması gerekmektedir. En önemlisi, hiçbir teknik indikatör tek başına %100 başarılı değildir. Bu sistemi, kapsamlı bir analiz sürecinin bir parçası olarak kullanmak, risk yönetimi kurallarıyla desteklemek ve sürekli performansını takip etmek başarılı sonuçlar için kritik öneme sahiptir. Geçmiş performans gelecekteki sonuçları garanti etmez. Her yatırım kararında kendi risk toleransınızı göz önünde bulundurun ve gerektiğinde profesyonel destek alın.

Trading View Pine Script Kodu

// Bu, Pine Script™ kodu Mozilla Kamu Lisansı 2.0 (MPL-2.0) altında lisanslandı
// © krstsntrk © BorsaPin codeispriority
//@version=6

indicator("BorsaPin Ema Sinyal Tablosu", overlay=true)

// Borsapin Ema Sinyal Tablosu
// Kısa Vade Fibonacci EMA'ları (5, 8, 13, 21)
ema5  = input.int(5, "EMA 5", minval=1, group="Kısa Vade")
ema8  = input.int(8, "EMA 8", minval=1, group="Kısa Vade")
ema13 = input.int(13, "EMA 13", minval=1, group="Kısa Vade")
ema21a = input.int(21, "EMA 21", minval=1, group="Kısa Vade")

// Orta Vade Fibonacci EMA'ları (34, 55)
ema34  = input.int(34, "EMA 34", minval=1, group="Orta Vade")
ema55a = input.int(55, "EMA 55", minval=1, group="Orta Vade")

// Uzun Vade Fibonacci EMA'ları (89, 144)
ema89  = input.int(89, "EMA 89", minval=1, group="Uzun Vade")
ema144 = input.int(144, "EMA 144", minval=1, group="Uzun Vade")

// Görsel ayarlar
showTable = input.bool(true, "Tabloyu Göster")
tablePos = input.string("Sağ Üst", "Tablo Konumu", options=["Sol Üst", "Sağ Üst", "Sol Alt", "Sağ Alt"])
showEMAs = input.bool(true, "EMA Çizgilerini Göster", group="Görsel")
onlyDaily = input.bool(false, "Sadece Günlük Verileri Göster", group="Görsel")

// Günlük Zaman Dilimi Verileri 
[dailyClose, dailyFib5, dailyFib8, dailyFib13, dailyFib21a, dailyFib34, dailyFib55a, dailyFib89, dailyFib144] =  request.security(syminfo.tickerid, "1D", [close, ta.ema(close, ema5), ta.ema(close, ema8), ta.ema(close, ema13), ta.ema(close, ema21a),  ta.ema(close, ema34), ta.ema(close, ema55a), ta.ema(close, ema89), ta.ema(close, ema144)])

// Günlük veriler için sinyal hesaplamaları
dailyEgimYukari = dailyFib5 > dailyFib5[1] and dailyFib8 > dailyFib8[1] and dailyFib13 > dailyFib13[1] and dailyFib21a > dailyFib21a[1]
dailyEgimAsagi = dailyFib21a < dailyFib21a[1] and dailyFib13 < dailyFib13[1]

// Günlük sinyaller
dailySinyalKisaAL = dailyClose > dailyFib5 and dailyClose > dailyFib8 and dailyClose > dailyFib13 and dailyClose > dailyFib21a and dailyEgimYukari
dailySinyalKisaSAT = dailyClose < dailyFib21a and dailyEgimAsagi
dailySinyalOrtaAL = dailyClose > dailyFib34 and dailyClose > dailyFib55a
dailySinyalOrtaSAT = dailyClose < dailyFib55a
dailySinyalUzunAL = dailyClose > dailyFib89 and dailyClose > dailyFib144
dailySinyalUzunSAT = dailyClose < dailyFib144
// Fibonacci EMA Hesapları
fib5   = ta.ema(close, ema5)
fib8   = ta.ema(close, ema8)
fib13  = ta.ema(close, ema13)
fib21a = ta.ema(close, ema21a)

fib34  = ta.ema(close, ema34)
fib55a = ta.ema(close, ema55a)

fib89  = ta.ema(close, ema89)
fib144 = ta.ema(close, ema144)

// Günlük sinyal durumları
var string dailyKisaSinyalDurumu = "BEKLİYOR"
var string dailyOrtaSinyalDurumu = "BEKLİYOR"
var string dailyUzunSinyalDurumu = "BEKLİYOR"

var int dailyKisaBarSayaci = 0
var int dailyOrtaBarSayaci = 0
var int dailyUzunBarSayaci = 0

var string dailyTarihKisa = "Yok"
var string dailyTarihOrta = "Yok"
var string dailyTarihUzun = "Yok"

// Günlük sinyal mantıkları
if dailySinyalKisaAL and dailyKisaSinyalDurumu[1] != "AL"
    dailyKisaSinyalDurumu := "AL"
    dailyKisaBarSayaci := 1
    dailyTarihKisa := str.format("{0,date,dd.MM.yyyy}", time)
else if dailyKisaSinyalDurumu[1] == "AL" and dailyClose > dailyFib21a and dailyEgimYukari
    dailyKisaSinyalDurumu := "AL"
    dailyKisaBarSayaci += 1
else if dailySinyalKisaSAT
    dailyKisaSinyalDurumu := "SAT"
    if dailyKisaSinyalDurumu[1] != "SAT"
        dailyKisaBarSayaci := 1
        dailyTarihKisa := str.format("{0,date,dd.MM.yyyy}", time)
    else
        dailyKisaBarSayaci += 1
else
    if dailyKisaSinyalDurumu[1] == "AL"
        dailyKisaSinyalDurumu := "AL"
        dailyKisaBarSayaci += 1
    else
        dailyKisaSinyalDurumu := "BEKLİYOR"
        dailyKisaBarSayaci := 0

if dailySinyalOrtaAL
    dailyOrtaSinyalDurumu := "AL"
    if dailyOrtaSinyalDurumu[1] != "AL"
        dailyOrtaBarSayaci := 1
        dailyTarihOrta := str.format("{0,date,dd.MM.yyyy}", time)
    else
        dailyOrtaBarSayaci += 1
else if dailySinyalOrtaSAT
    dailyOrtaSinyalDurumu := "SAT"
    if dailyOrtaSinyalDurumu[1] != "SAT"
        dailyOrtaBarSayaci := 1
        dailyTarihOrta := str.format("{0,date,dd.MM.yyyy}", time)
    else
        dailyOrtaBarSayaci += 1
else
    dailyOrtaSinyalDurumu := "BEKLİYOR"
    dailyOrtaBarSayaci := 0

if dailySinyalUzunAL
    dailyUzunSinyalDurumu := "AL"
    if dailyUzunSinyalDurumu[1] != "AL"
        dailyUzunBarSayaci := 1
        dailyTarihUzun := str.format("{0,date,dd.MM.yyyy}", time)
    else
        dailyUzunBarSayaci += 1
else if dailySinyalUzunSAT
    dailyUzunSinyalDurumu := "SAT"
    if dailyUzunSinyalDurumu[1] != "SAT"
        dailyUzunBarSayaci := 1
        dailyTarihUzun := str.format("{0,date,dd.MM.yyyy}", time)
    else
        dailyUzunBarSayaci += 1
else
    dailyUzunSinyalDurumu := "BEKLİYOR"
    dailyUzunBarSayaci := 0

// EMA Çizgileri
plot(showEMAs ? fib5 : na, "EMA 5", color=color.new(color.maroon, 50), linewidth=1)
plot(showEMAs ? fib8 : na, "EMA 8", color=color.new(color.blue, 50), linewidth=1)
plot(showEMAs ? fib13 : na, "EMA 13", color=color.new(color.green, 50), linewidth=1)
plot(showEMAs ? fib21a : na, "EMA 21", color=color.new(color.orange, 30), linewidth=1)
plot(showEMAs ? fib34 : na, "EMA 34", color=color.new(color.purple, 30), linewidth=1)
plot(showEMAs ? fib55a : na, "EMA 55", color=color.new(color.red, 20), linewidth=2)
plot(showEMAs ? fib89 : na, "EMA 89", color=color.new(color.fuchsia, 40), linewidth=2)
plot(showEMAs ? fib144 : na, "EMA 144", color=color.new(color.aqua, 40), linewidth=2)

// KISA VADE Sinyalleri  Detaylı Sinyal Mantığı  Her Vade İçin Ayrı 
// Eğim kontrolü
kisaVadeEgimYukari = fib5 > fib5[1] and fib8 > fib8[1] and fib13 > fib13[1] and fib21a > fib21a[1]

// AL sinyali: Tüm EMA'ların üzerinde ve eğim yukarı
sinyalKisaAL = close > fib5 and close > fib8 and close > fib13 and close > fib21a and kisaVadeEgimYukari

// SAT sinyali: EMA 21'in altına düşmesi ve eğim aşağı
kisaVadeEgimAsagi = fib21a < fib21a[1] and fib13 < fib13[1]
sinyalKisaSAT = close < fib21a and kisaVadeEgimAsagi

// ORTA VADE Sinyalleri (Kısa vade mantığı uygulandı)
sinyalOrtaAL = close > fib34 and close > fib55a and fib34 > fib55a

sinyalOrtaSAT = close < fib55a

// UZUN VADE Sinyalleri (Sadece fiyat kontrolü)
sinyalUzunAL = close > fib89 and close > fib144

sinyalUzunSAT = close < fib144

// Sinyal Durumu Değişkenleri 
var string kisaSinyalDurumu = "BEKLİYOR"
var string ortaSinyalDurumu = "BEKLİYOR"
var string uzunSinyalDurumu = "BEKLİYOR"

var int kisaBarSayaci = 0
var int ortaBarSayaci = 0
var int uzunBarSayaci = 0

var string tarihKisa = "Yok"
var string tarihOrta = "Yok"
var string tarihUzun = "Yok"

//  KISA VADE Sinyal Mantığı - Sürekli AL Mantığı
if sinyalKisaAL and kisaSinyalDurumu[1] != "AL"
    // İlk AL sinyali - tarih ve bar sayacı sıfırla
    kisaSinyalDurumu := "AL"
    kisaBarSayaci := 1
    tarihKisa := str.format("{0,date,dd.MM.yyyy}", time)
else if kisaSinyalDurumu[1] == "AL" and close > fib21a and kisaVadeEgimYukari
    // AL sinyali devam ediyor - EMA 21 üzerinde ve eğim yukarı
    kisaSinyalDurumu := "AL"
    kisaBarSayaci += 1
else if sinyalKisaSAT
    // SAT sinyali
    kisaSinyalDurumu := "SAT"
    if kisaSinyalDurumu[1] != "SAT"
        kisaBarSayaci := 1
        tarihKisa := str.format("{0,date,dd.MM.yyyy}", time)
    else
        kisaBarSayaci += 1
else
    // Belirsizlik durumu
    if kisaSinyalDurumu[1] == "AL"
        kisaSinyalDurumu := "AL"
        kisaBarSayaci += 1
    else
        kisaSinyalDurumu := "BEKLİYOR"
        kisaBarSayaci := 0

//  ORTA VADE Sinyal Mantığı
if sinyalOrtaAL
    ortaSinyalDurumu := "AL"
    if ortaSinyalDurumu[1] != "AL"
        ortaBarSayaci := 0
        tarihOrta := str.format("{0,date,dd.MM.yyyy} ", time)
    else
        ortaBarSayaci += 1
else if sinyalOrtaSAT
    ortaSinyalDurumu := "SAT"
    if ortaSinyalDurumu[1] != "SAT"
        ortaBarSayaci := 0
        tarihOrta := str.format("{0,date,dd.MM.yyyy} ", time)
    else
        ortaBarSayaci += 1
else
    ortaSinyalDurumu := "BEKLİYOR"
    ortaBarSayaci := 0

// UZUN VADE Sinyal Mantığı 
if sinyalUzunAL
    uzunSinyalDurumu := "AL"
    if uzunSinyalDurumu[1] != "AL"
        uzunBarSayaci := 0
        tarihUzun := str.format("{0,date,dd.MM.yyyy} ", time)
    else
        uzunBarSayaci += 1
else if sinyalUzunSAT
    uzunSinyalDurumu := "SAT"
    if uzunSinyalDurumu[1] != "SAT"
        uzunBarSayaci := 0
        tarihUzun := str.format("{0,date,dd.MM.yyyy}", time)
    else
        uzunBarSayaci += 1
else
    uzunSinyalDurumu := "BEKLİYOR"
    uzunBarSayaci := 0

// Tablo konumu belirleme
tablePosition = if tablePos == "Sol Üst"
    position.top_left
else if tablePos == "Sağ Üst"
    position.top_right
else if tablePos == "Sol Alt"
    position.bottom_left
else if tablePos == "Sağ Alt"
    position.bottom_right
else
    position.top_right

// Tablo Oluşturma 
if showTable
    var table tablo = table.new(tablePosition, 5, 4, border_width=1, bgcolor=color.white, border_color=color.gray)

    // Başlık satırı
    table.cell(tablo, 0, 0, "Vade", bgcolor=color.new(color.blue, 80), text_color=color.black, text_size=size.small)
    table.cell(tablo, 1, 0, "Sinyal Tarihi", bgcolor=color.new(color.blue, 80), text_color=color.black, text_size=size.small)
    table.cell(tablo, 2, 0, "Bar", bgcolor=color.new(color.blue, 80), text_color=color.black, text_size=size.small)
    table.cell(tablo, 3, 0, "Durum", bgcolor=color.new(color.blue, 80), text_color=color.black, text_size=size.small)
    table.cell(tablo, 4, 0, "Güç", bgcolor=color.new(color.blue, 80), text_color=color.black, text_size=size.small)

    //  KISA VADE SATIRI 
    // Hangi veriler kullanılacak
    useKisaSinyalDurumu = onlyDaily ? dailyKisaSinyalDurumu : kisaSinyalDurumu
    useKisaBarSayaci = onlyDaily ? dailyKisaBarSayaci : kisaBarSayaci
    useTarihKisa = onlyDaily ? dailyTarihKisa : tarihKisa
    useKisaClose = onlyDaily ? dailyClose : close
    useKisaFib5 = onlyDaily ? dailyFib5 : fib5
    useKisaFib8 = onlyDaily ? dailyFib8 : fib8
    
    kisaRenk = if useKisaSinyalDurumu == "AL"
        if useKisaClose < useKisaFib8 and useKisaClose > useKisaFib5
            color.new(color.green, 40) // Orta Güçlü AL
        else if useKisaClose < useKisaFib5
            color.new(color.green, 60) // Zayıf AL
        else
            color.new(color.green, 20) // Güçlü AL
    else if useKisaSinyalDurumu == "SAT"
        color.new(color.red, 20)
    else
        color.new(color.gray, 40)
    
    kisaDurumText = if useKisaSinyalDurumu == "AL" and useKisaClose < useKisaFib8
        "AL (Zayıf)"
    else if useKisaSinyalDurumu == "AL" and useKisaClose > useKisaFib8
        "AL (Güçlü)"
    else
        useKisaSinyalDurumu

    kisaGuc = if useKisaSinyalDurumu == "AL" 
        if useKisaBarSayaci <= 5
            "⭐⭐⭐"
        else if useKisaBarSayaci <= 15
            "⭐⭐"
        else if useKisaBarSayaci <= 30
            "⭐"
        else
            ""
    else if useKisaSinyalDurumu == "SAT"
        if useKisaBarSayaci <= 5
            "⭐⭐⭐"
        else if useKisaBarSayaci <= 15
            "⭐⭐"
        else if useKisaBarSayaci <= 30
            "⭐"
        else
            ""
    else
        "⏳"

    kisaBarText = useKisaSinyalDurumu == "BEKLİYOR" ? "" : str.tostring(useKisaBarSayaci)

    table.cell(tablo, 0, 1, "Kısa Vade", text_size=size.small)
    table.cell(tablo, 1, 1, useTarihKisa, text_size=size.tiny)
    table.cell(tablo, 2, 1, kisaBarText, text_size=size.small)
    table.cell(tablo, 3, 1, kisaDurumText, bgcolor=kisaRenk, text_color=color.white, text_size=size.small)
    table.cell(tablo, 4, 1, kisaGuc, text_size=size.small)

    // ORTA VADE SATIRI 
    ortaRenk = if ortaSinyalDurumu == "AL"
        if close < fib34 and close > fib55a
            color.new(color.green, 60) // Zayıf AL
        else if close > fib34
            color.new(color.green, 20) // Güçlü AL
        else
            color.new(color.green, 40) // Orta AL
    else if ortaSinyalDurumu == "SAT"
        color.new(color.red, 20)
    else
        color.new(color.gray, 40)
        
    ortaDurumText = if ortaSinyalDurumu == "AL" and close < fib34
        "AL (Zayıf)"
    else if ortaSinyalDurumu == "AL" and close > fib34
        "AL (Güçlü)"
    else
        ortaSinyalDurumu
        
    ortaGuc = if ortaSinyalDurumu == "AL" 
        if ortaBarSayaci <= 5 
            "⭐⭐⭐" 
        else if ortaBarSayaci <= 15 
            "⭐⭐" 
        else if ortaBarSayaci <= 30 
            "⭐" 
        else 
            ""
    else if ortaSinyalDurumu == "SAT" 
        if ortaBarSayaci <= 5 
            "⭐⭐⭐" 
        else if ortaBarSayaci <= 15 
            "⭐⭐" 
        else if ortaBarSayaci <= 30 
            "⭐" 
        else 
            ""
    else 
        "⏳"
        
    ortaBarText = ortaSinyalDurumu == "BEKLİYOR" ? "" : str.tostring(ortaBarSayaci)

    table.cell(tablo, 0, 2, "Orta Vade", text_size=size.small)
    table.cell(tablo, 1, 2, tarihOrta, text_size=size.tiny)
    table.cell(tablo, 2, 2, ortaBarText, text_size=size.small)
    table.cell(tablo, 3, 2, ortaDurumText, bgcolor=ortaRenk, text_color=color.white, text_size=size.small)
    table.cell(tablo, 4, 2, ortaGuc, text_size=size.small)

    //  UZUN VADE SATIRI 
    uzunRenk = if uzunSinyalDurumu == "AL"
        if close < fib89 and close > fib144
            color.new(color.green, 60) // Zayıf AL
        else if close > fib89
            color.new(color.green, 20) // Güçlü AL
        else
            color.new(color.green, 40) // Orta AL
    else if uzunSinyalDurumu == "SAT"
        color.new(color.red, 20)
    else
        color.new(color.gray, 40)
        
    uzunDurumText = if uzunSinyalDurumu == "AL" and close < fib89
        "AL (Zayıf)"
    else if uzunSinyalDurumu == "AL" and close > fib89
        "AL (Güçlü)"
    else
        uzunSinyalDurumu
        
    uzunGuc = if uzunSinyalDurumu == "AL" 
        if uzunBarSayaci <= 5 
            "⭐⭐⭐⭐" 
        else if uzunBarSayaci <= 15 
            "⭐⭐⭐" 
        else if uzunBarSayaci <= 30 
            "⭐⭐" 
        else if uzunBarSayaci <= 50 
            "⭐" 
        else 
            ""
    else if uzunSinyalDurumu == "SAT" 
        if uzunBarSayaci <= 5 
            "⭐⭐⭐⭐" 
        else if uzunBarSayaci <= 15 
            "⭐⭐⭐" 
        else if uzunBarSayaci <= 30 
            "⭐⭐" 
        else if uzunBarSayaci <= 50 
            "⭐" 
        else 
            ""
    else 
        "⏳"
        
    uzunBarText = uzunSinyalDurumu == "BEKLİYOR" ? "" : str.tostring(uzunBarSayaci)

    table.cell(tablo, 0, 3, "Uzun Vade", text_size=size.small)
    table.cell(tablo, 1, 3, tarihUzun, text_size=size.tiny)
    table.cell(tablo, 2, 3, uzunBarText, text_size=size.small)
    table.cell(tablo, 3, 3, uzunDurumText, bgcolor=uzunRenk, text_color=color.white, text_size=size.small)
    table.cell(tablo, 4, 3, uzunGuc, text_size=size.small)

 

Python BorsaPin Lineer Regresyon ve Pearson Analizi Betiği

06 Ağustos 2025 BorsaPin, Python, Teknik Analizborsa analizi, borsa stratejileri, borsa verisi analizi, BorsaPin, breakout sinyalleri, EMA dizilimi, Excel dosyası, Excel raporu, Excel veri işleme, finansal analiz, finansal analiz araçları, finansal korelasyon, finansal raporlama., finansal veri analizi, finansal veri görselleştirme, fırsat analizi, hisse senedi analizi, hisse senedi trendleri, istatistiksel analiz, kanal fırsatları, lineer regresyon analizi, Pearson korelasyonu, Python betiği, Python ile yatırım analizi, regresyon analizi Python, Teknik Analiz, veri analizi, yatırım analiz araçları, yatırım fırsatları, yatırım fırsatları tespiti, yatırım kararları, yatırımcılar için araçlar

Bu Python betiği, X_01_BorsaPin_StokData.py  Python betiğiyle oluşturulan StokData/Kapanis klasöründeki hisse kapanış verilerinden lineer regresyon trend analizi ve Pearson korelasyon ölçümleri yaparak detaylı teknik analiz raporu üretir. Analizler, Excel formatında renklendirilmiş ve filtrelenebilir şekilde kayıt altına alınır.

Terminalden şu iki komutu çalıştırın .
python.exe -m pip install --upgrade pip
pip install pandas numpy scipy colorama openpyxl

Kodun Temel Özellikleri

Lineer Regresyon Analizi: Kapanış fiyatları üzerinden trend çizgisi (slope), kanal bandı, standart sapma gibi metrikleri hesaplar.
Pearson Korelasyon: Trendin gücünü ölçmek için farklı periyotlarda Pearson korelasyon katsayısı hesaplanır.

 

Fırsat Tespiti:

Kanal Altı Fırsatları: Alt banda yakın fiyat hareketleri ve güçlü korelasyon içeren hisseler.

Breakout Adayları: Üst banda yakın olup yükseliş sinyali veren hisseler.

EMA Dizilim Entegrasyonu: Farklı script tarafından oluşturulan EMA analizleriyle birleştirilebilir.

Otomatik Excel Raporu: Tüm veriler biçimlendirilmiş bir Excel dosyasına kaydedilir (filtrelenebilir, renklendirilmiş).

Başarısız Dosya Takibi: Hatalı veriler ayrı bir .txt dosyasına kaydedilir. Analiz Süreci Otomatik Gerçekleşir:

Tüm dosyalar sırasıyla işlenir. Lineer regresyon analizleri yapılır. Fırsatlar belirlenir. Sonuçlar Excel ve TXT dosyalarına kaydedilir.

Üretilen Dosyalar

StokData/lineer_regresyon_analiz.xlsx → Ana analiz dosyası
StokData/LinearRegression/lineer_regresyon_analiz_YYYY-MM-DD.xlsx → Arşiv dosyası

basarisiz_regresyon_dosyalari.txt → Başarısız analizlerin listesi

Excel Sayfaları
TumSonuclar: Tüm hisse ve periyot sonuçları
IdealPearson: En güçlü Pearson korelasyonuna sahip hisseler
KanalFirsatlari_Top50: Kanal altına yakın fırsatlar
BreakoutAdaylari_Top50: Yükselişe aday hisseler
Periyot_XXX: Her analiz periyodu için ayrı sayfalar
Istatistikler: Genel başarı ve analiz özetleri

Avantajları

Otomatik, hızlı ve güvenilir teknik analiz.  Yatırım kararlarını destekleyecek fırsat ve sinyal tespiti. Excel üzerinden kolay görsel analiz ve filtreleme imkânı

Bu betik, teknik analizde trend doğruluğunu ve fırsatları istatistiksel olarak belirlemek isteyen yatırımcılar için güçlü bir araçtır. Özellikle BIST verileriyle çalışan sistemlerde regresyon ve Pearson tabanlı analiz ile öne çıkan hisseleri kolayca tespit etmeye yardımcı olur.

LinReg tarama çalışmamızı X_05_BorsaPin_LinReg_Tarama.py adıyla kayıt edebilirsiniz.
Python Betiği

import pandas as pd
import numpy as np
import os
import glob
from scipy.stats import linregress, pearsonr
from datetime import datetime, timedelta
from colorama import Fore, init
from openpyxl.styles import Font, PatternFill, Alignment
from openpyxl.utils import get_column_letter
from typing import List, Dict, Optional

"""
      Borsapin StokData/Kapanis klasöründeki hisse verilerinden Lineer Regresyon ve Pearson analizi yapar
      www.kursatsenturk.com

      """

init(autoreset=True)


class LinearRegressionAnalyzer:
    def __init__(self):
        self.pearson_periods = [55, 89, 144, 233, 370, 610, 987]
        self.analysis_periods = [55, 89, 144, 233, 370, 610, 987]  # Özel analiz periyotları
        self.successful_files = []
        self.failed_files = []

        # Sonuç listeleri
        self.all_results = []
        self.period_results = {period: [] for period in self.pearson_periods}
        self.ideal_pearson = []
        self.channel_opportunities = []
        self.breakout_candidates = []
        self.statistics = {}

    @staticmethod
    def calculate_regression(data_df: pd.DataFrame, period: int) -> Optional[Dict]:
        """Lineer regresyon ve kanal hesaplama"""
        try:
            # Son 'period' a kadar veriyi al
            data_df = data_df.tail(period).copy()
            if len(data_df) < period:
                return None

            # X ekseni (zaman) ve Y ekseni (fiyat) değerleri
            x = np.arange(len(data_df))
            y = data_df["Kapanış"].values

            # Lineer regresyon hesaplama
            slope, intercept, r_value, p_value, std_err = linregress(x, y)

            # Trend çizgisi hesaplama
            trend_line = intercept + slope * x

            # Residual (artık) değerler ve standart sapma
            residuals = y - trend_line
            std_dev = np.std(residuals)

            # Kanal bantları (2 standart sapma)
            upper_channel = trend_line + 2 * std_dev
            lower_channel = trend_line - 2 * std_dev

            # Pearson korelasyon katsayısı
            corr, _ = pearsonr(x, y)

            # Son değerler
            upper_channel_value = round(float(upper_channel[-1]), 2)
            lower_channel_value = round(float(lower_channel[-1]), 2)
            trend_value = round(float(trend_line[-1]), 2)
            last_price = float(y[-1])

            # Yüzde farkları
            upper_diff_pct = round((last_price - upper_channel_value) / last_price * 100, 2)
            lower_diff_pct = round((last_price - lower_channel_value) / last_price * 100, 2)
            trend_diff_pct = round((last_price - trend_value) / last_price * 100, 2)

            # Trend yönü ve güç
            trend_direction = "Yükseliş" if slope > 0 else "Düşüş"
            trend_strength = "Güçlü" if abs(slope) > 0.05 else "Orta" if abs(slope) > 0.01 else "Zayıf"

            # Kanal pozisyonu
            channel_position = "Üst Bant" if upper_diff_pct >= -2 else "Alt Bant" if lower_diff_pct <= 2 else "Orta"

            return {
                "Periyot": period,
                "Kanal_Ust": upper_channel_value,
                "Kanal_Alt": lower_channel_value,
                "Trend_Cizgisi": trend_value,
                "Ust_Fark_Pct": upper_diff_pct,
                "Alt_Fark_Pct": lower_diff_pct,
                "Trend_Fark_Pct": trend_diff_pct,
                "Trend_Yonu": trend_direction,
                "Trend_Gucu": trend_strength,
                "Kanal_Pozisyonu": channel_position,
                "Pearson": round(corr, 4),
                "R_Kare": round(r_value ** 2, 4),
                "Slope": round(slope, 6),
                "P_Value": round(p_value, 6),
                "Std_Error": round(std_err, 6)
            }

        except Exception as e:
            print(f"{Fore.RED}❌ Regresyon hesaplama hatası (Period {period}): {e}")
            return None

    def process_single_file(self, file_path: str) -> bool:
        """Tek dosya için lineer regresyon analizi"""
        ticker_name = None
        try:
            # Dosya adından hisse adını alma
            file_name = os.path.basename(file_path)
            ticker_name = os.path.splitext(file_name)[0]

            print(f"{Fore.YELLOW} Lineer regresyon analizi: {ticker_name}...")

            # Excel dosyasını okuma
            df = pd.read_excel(file_path)

            # Gerekli sütunların varlığını kontrol etme
            if 'Tarih' not in df.columns or 'Kapanış' not in df.columns:
                raise ValueError("Tarih veya Kapanış sütunu bulunamadı")

            # Veri temizleme ve sıralama
            df = df[["Tarih", "Kapanış"]].dropna()
            df["Tarih"] = pd.to_datetime(df["Tarih"])
            df = df.sort_values("Tarih").reset_index(drop=True)
            df["Kapanış"] = pd.to_numeric(df["Kapanış"], errors='coerce')
            df = df.dropna()

            if df.empty:
                raise ValueError("Veri boş veya geçersiz")

            last_close = round(float(df["Kapanış"].iloc[-1]), 2)
            last_date = df["Tarih"].iloc[-1]

            print(f"{Fore.CYAN}   ⚡ Periyotlar hesaplanıyor: ", end="")

            # Her periyot için analiz
            ticker_pearson_data = {"Hisse_Adi": ticker_name, "Kapanış": last_close, "Tarih": last_date}

            for i, period in enumerate(self.pearson_periods):
                print(f"{period}", end="")

                result = self.calculate_regression(df.copy(), period)
                if result:
                    # Ana sonuç listesine ekle
                    main_result = {
                        "Hisse_Adi": ticker_name,
                        "Kapanış": last_close,
                        "Tarih": last_date,
                        **result
                    }
                    self.all_results.append(main_result)

                    # Periyot bazlı sonuçlara ekle
                    self.period_results[period].append(main_result)

                    # İdeal Pearson için veri toplama
                    ticker_pearson_data[f"Pearson_{period}"] = result["Pearson"]
                    ticker_pearson_data[f"Kanal_Pozisyon_{period}"] = result["Kanal_Pozisyonu"]
                    ticker_pearson_data[f"Alt_Fark_{period}"] = result["Alt_Fark_Pct"]
                    ticker_pearson_data[f"Ust_Fark_{period}"] = result["Ust_Fark_Pct"]

                if i < len(self.pearson_periods) - 1:
                    print(", ", end="")
            print()

            # İdeal Pearson listesine ekle
            self.ideal_pearson.append(ticker_pearson_data)

            # Özel analizler için kontrol
            self.analyze_opportunities(ticker_name, last_close, last_date, df)

            print(f"{Fore.GREEN}✅ {ticker_name} analizi tamamlandı.")
            self.successful_files.append(ticker_name)
            return True

        except Exception as e:
            print(f"{Fore.RED}❌ {ticker_name if ticker_name else file_path} için hata: {e}")
            self.failed_files.append(os.path.basename(file_path))
            return False

    def analyze_opportunities(self, ticker_name: str, last_close: float, last_date, df: pd.DataFrame):
        """Fırsat analizi - kanal alt bandı ve breakout adayları"""
        try:
            for period in self.analysis_periods:
                result = self.calculate_regression(df.copy(), period)
                if result:
                    # Alt banda yakın fırsatlar (Alt fark <= 4% ve Pearson >= 0.7)
                    if (-2 <= result["Alt_Fark_Pct"] <= 4 and
                            abs(result["Pearson"]) >= 0.7):
                        self.channel_opportunities.append({
                            "Hisse_Adi": ticker_name,
                            "Kapanış": last_close,
                            "Tarih": last_date,
                            "Periyot": period,
                            "Alt_Fark_Pct": result["Alt_Fark_Pct"],
                            "Pearson": result["Pearson"],
                            "Trend_Yonu": result["Trend_Yonu"],
                            "Kanal_Alt": result["Kanal_Alt"],
                            "Kanal_Ust": result["Kanal_Ust"],
                            "Potansiyel_Kazanc": round((result["Kanal_Ust"] - last_close) / last_close * 100, 2)
                        })

                    # Breakout adayları (Üst fark >= -4% ve Pearson >= 0.8)
                    if (-4 <= result["Ust_Fark_Pct"] <= 2 and
                            abs(result["Pearson"]) >= 0.8):
                        self.breakout_candidates.append({
                            "Hisse_Adi": ticker_name,
                            "Kapanış": last_close,
                            "Tarih": last_date,
                            "Periyot": period,
                            "Ust_Fark_Pct": result["Ust_Fark_Pct"],
                            "Pearson": result["Pearson"],
                            "Trend_Yonu": result["Trend_Yonu"],
                            "Kanal_Ust": result["Kanal_Ust"],
                            "Hedef_Fiyat": round(result["Kanal_Ust"] * 1.05, 2)  # %5 üst hedef
                        })

        except Exception as e:
            print(f"{Fore.RED}❌ Fırsat analizi hatası ({ticker_name}): {e}")

    def calculate_statistics(self):
        """İstatistik hesaplama"""
        try:
            print(f"{Fore.CYAN} İstatistikler hesaplanıyor...")

            # Genel istatistikler
            stats = {
                "Toplam_Analiz_Edilen": len(self.successful_files),
                "Basarisiz_Dosya": len(self.failed_files)
            }

            # Periyot bazlı istatistikler
            for period in self.pearson_periods:
                period_data = self.period_results[period]
                if period_data:
                    pearson_values = [item["Pearson"] for item in period_data if item.get("Pearson")]
                    stats[f"Ortalama_Pearson_{period}"] = round(np.mean(pearson_values), 4) if pearson_values else 0
                    stats[f"Yuksek_Pearson_Sayisi_{period}"] = len([p for p in pearson_values if abs(p) >= 0.8])

            # Fırsat istatistikleri
            stats["Kanal_Alt_Firsatlari"] = len(self.channel_opportunities)
            stats["Breakout_Adaylari"] = len(self.breakout_candidates)

            # Trend analizi
            trend_up = len([item for item in self.all_results if item.get("Trend_Yonu") == "Yükseliş"])
            trend_down = len([item for item in self.all_results if item.get("Trend_Yonu") == "Düşüş"])
            stats["Yukselis_Trendi"] = trend_up
            stats["Dusus_Trendi"] = trend_down

            self.statistics = stats
            return stats

        except Exception as e:
            print(f"{Fore.RED}❌ İstatistik hesaplama hatası: {e}")
            return {}

    @staticmethod
    def find_input_files(input_folder="StokData/Kapanis/"):
        """Giriş dosyalarını bulma"""
        try:
            pattern = os.path.join(input_folder, "*.xlsx")
            files = glob.glob(pattern)

            if not files:
                print(f"{Fore.RED}❌ {input_folder} klasöründe Excel dosyası bulunamadı!")
                return []

            print(f"{Fore.BLUE} {len(files)} adet Excel dosyası bulundu.")
            return files

        except Exception as e:
            print(f"{Fore.RED}❌ Dosya arama hatası: {e}")
            return []

    def merge_ema_data(self):
        """EMA dizilim verilerini birleştirme"""
        try:
            ema_file = "StokData/idealema_analiz.xlsx"
            if os.path.exists(ema_file):
                print(f"{Fore.CYAN} EMA verileri birleştiriliyor...")
                ema_df = pd.read_excel(ema_file, sheet_name="IdealEMAUp")
                ema_mapping = dict(zip(ema_df["Hisse_Adi"], ema_df["EMA_Dizilim"]))

                # Tüm sonuçlara EMA bilgisi ekle
                for result in self.all_results:
                    result["EMA_Dizilim"] = ema_mapping.get(result["Hisse_Adi"], "Bilinmiyor")

                for result in self.ideal_pearson:
                    result["EMA_Dizilim"] = ema_mapping.get(result["Hisse_Adi"], "Bilinmiyor")

                print(f"{Fore.GREEN}✅ EMA verileri başarıyla birleştirildi.")
            else:
                print(f"{Fore.YELLOW}⚠️  EMA dosyası bulunamadı: {ema_file}")

        except Exception as e:
            print(f"{Fore.RED}❌ EMA veri birleştirme hatası: {e}")

    @staticmethod
    def write_sheet_with_formatting(excel_writer, df, sheet_name, freeze_panes=None):
        """Excel sayfası yazma ve biçimlendirme"""
        try:
            if isinstance(df, list):
                df = pd.DataFrame(df)

            if df.empty:
                df = pd.DataFrame([{"Mesaj": "Veri bulunamadı"}])

            df.to_excel(excel_writer, sheet_name=sheet_name, index=False)
            ws = excel_writer.sheets[sheet_name]

            # Başlık biçimlendirme
            header_fill = PatternFill(start_color='4472C4', end_color='4472C4', fill_type='solid')
            for col_num, column in enumerate(df.columns, 1):
                cell = ws.cell(row=1, column=col_num)
                cell.font = Font(bold=True, color='FFFFFF')
                cell.fill = header_fill
                cell.alignment = Alignment(horizontal='center')

                # Sütun genişlikleri
                if any(keyword in str(column) for keyword in ['Tarih', 'Date']):
                    ws.column_dimensions[get_column_letter(col_num)].width = 15
                elif any(keyword in str(column) for keyword in ['Hisse', 'CODE']):
                    ws.column_dimensions[get_column_letter(col_num)].width = 12
                elif any(keyword in str(column) for keyword in ['Pearson', 'Fark', 'Pct']):
                    ws.column_dimensions[get_column_letter(col_num)].width = 18
                else:
                    ws.column_dimensions[get_column_letter(col_num)].width = 20

            # Veri satırlarını biçimlendirme
            for row_num in range(2, len(df) + 2):
                for col_num in range(1, len(df.columns) + 1):
                    cell = ws.cell(row=row_num, column=col_num)
                    cell.alignment = Alignment(horizontal='center')
                    column_name = df.columns[col_num - 1]

                    # Pearson değerleri için renklendirme
                    if 'Pearson' in str(column_name) and isinstance(cell.value, (int, float)):
                        if abs(cell.value) >= 0.9:
                            cell.fill = PatternFill(start_color='00FF00', end_color='00FF00', fill_type='solid')
                        elif abs(cell.value) >= 0.8:
                            cell.fill = PatternFill(start_color='90EE90', end_color='90EE90', fill_type='solid')
                        elif abs(cell.value) >= 0.7:
                            cell.fill = PatternFill(start_color='FFFF99', end_color='FFFF99', fill_type='solid')

                    # Fark yüzdeleri için renklendirme
                    elif 'Alt_Fark' in str(column_name) and isinstance(cell.value, (int, float)):
                        if -2 <= cell.value <= 4:
                            cell.fill = PatternFill(start_color='FFFFCC', end_color='FFFFCC', fill_type='solid')

                    elif 'Ust_Fark' in str(column_name) and isinstance(cell.value, (int, float)):
                        if -4 <= cell.value <= 2:
                            cell.fill = PatternFill(start_color='FFCCCC', end_color='FFCCCC', fill_type='solid')

            # Freeze panes
            if freeze_panes:
                ws.freeze_panes = freeze_panes

            # AutoFilter ekleme (başlık satırına)
            if len(df) > 0:
                ws.auto_filter.ref = f"A1:{get_column_letter(len(df.columns))}{len(df) + 1}"

        except Exception as e:
            print(f"{Fore.RED}❌ Excel biçimlendirme hatası ({sheet_name}): {e}")

    def save_results(self):
        """Sonuçları Excel'e kaydetme"""
        try:
            # Klasörler oluşturma
            output_folder = "StokData/LinearRegression/"
            os.makedirs(output_folder, exist_ok=True)

            # Dosya isimleri
            today = datetime.today().strftime('%Y-%m-%d')
            main_file = os.path.join("StokData", "lineer_regresyon_analiz.xlsx")
            archive_file = os.path.join(output_folder, f"lineer_regresyon_analiz_{today}.xlsx")

            # Veri hazırlama
            print(f"{Fore.GREEN} Excel dosyası hazırlanıyor...")

            # Sıralama işlemleri
            # İdeal Pearson - maksimum mutlak Pearson değerine göre sırala
            ideal_pearson_df = pd.DataFrame(self.ideal_pearson)
            if not ideal_pearson_df.empty:
                pearson_cols = [col for col in ideal_pearson_df.columns if 'Pearson_' in col]
                if pearson_cols:
                    ideal_pearson_df['Max_Abs_Pearson'] = ideal_pearson_df[pearson_cols].abs().max(axis=1)
                    ideal_pearson_df = ideal_pearson_df.sort_values('Max_Abs_Pearson', ascending=False)

            # Kanal fırsatları - Pearson değerine göre sırala (İlk 50)
            channel_opp_df = pd.DataFrame(self.channel_opportunities)
            if not channel_opp_df.empty:
                channel_opp_df = channel_opp_df.sort_values(['Pearson', 'Alt_Fark_Pct'], ascending=[False, True]).head(
                    50)

            # Breakout adayları - Pearson değerine göre sırala (İlk 50)
            breakout_df = pd.DataFrame(self.breakout_candidates)
            if not breakout_df.empty:
                breakout_df = breakout_df.sort_values(['Pearson', 'Ust_Fark_Pct'], ascending=[False, False]).head(50)

            # İstatistikler
            stats_df = pd.DataFrame([
                {"Metrik": key, "Deger": value} for key, value in self.statistics.items()
            ])

            # Ana dosyayı kaydet
            print(f"{Fore.GREEN} Ana dosya kaydediliyor: {main_file}")
            with pd.ExcelWriter(main_file, engine='openpyxl') as writer:
                # Ana sayfalar
                self.write_sheet_with_formatting(writer, pd.DataFrame(self.all_results), "TumSonuclar", "A2")
                self.write_sheet_with_formatting(writer, ideal_pearson_df, "IdealPearson", "A2")
                self.write_sheet_with_formatting(writer, channel_opp_df, "KanalFirsatlari_Top50", "A2")
                self.write_sheet_with_formatting(writer, breakout_df, "BreakoutAdaylari_Top50", "A2")
                self.write_sheet_with_formatting(writer, stats_df, "Istatistikler", "A2")

                # Periyot bazlı sayfalar
                for period in self.pearson_periods:
                    period_df = pd.DataFrame(self.period_results[period])
                    if not period_df.empty:
                        period_df = period_df.sort_values('Pearson', ascending=False)
                        self.write_sheet_with_formatting(writer, period_df, f"Periyot_{period}", "A2")

            # Arşiv dosyasını kaydet
            print(f"{Fore.BLUE} Arşiv dosyası kaydediliyor: {archive_file}")
            with pd.ExcelWriter(archive_file, engine='openpyxl') as writer:
                self.write_sheet_with_formatting(writer, pd.DataFrame(self.all_results), "TumSonuclar", "A2")
                self.write_sheet_with_formatting(writer, ideal_pearson_df, "IdealPearson", "A2")
                self.write_sheet_with_formatting(writer, channel_opp_df, "KanalFirsatlari_Top50", "A2")
                self.write_sheet_with_formatting(writer, breakout_df, "BreakoutAdaylari_Top50", "A2")
                self.write_sheet_with_formatting(writer, stats_df, "Istatistikler", "A2")

                for period in self.pearson_periods:
                    period_df = pd.DataFrame(self.period_results[period])
                    if not period_df.empty:
                        period_df = period_df.sort_values('Pearson', ascending=False)
                        self.write_sheet_with_formatting(writer, period_df, f"Periyot_{period}", "A2")

            return True

        except Exception as e:
            print(f"{Fore.RED}❌ Sonuç kaydetme hatası: {e}")
            return False

    def print_summary(self):
        """Özet rapor"""
        total = len(self.successful_files) + len(self.failed_files)
        success_rate = (len(self.successful_files) / total * 100) if total > 0 else 0

        print(f"\n{Fore.CYAN} ===== LİNEER REGRESYON ANALİZ RAPORU =====")
        print(f"{Fore.BLUE} Analiz Periyotları: {', '.join(map(str, self.pearson_periods))}")
        print(f"{Fore.GREEN}✅ Başarılı: {len(self.successful_files)}")
        print(f"{Fore.RED}❌ Başarısız: {len(self.failed_files)}")
        print(f"{Fore.BLUE} Başarı oranı: {success_rate:.1f}%")

        print(f"\n{Fore.MAGENTA} SONUÇLAR:")
        print(f"{Fore.GREEN}   Toplam Analiz: {len(self.all_results)}")
        print(f"{Fore.YELLOW}   Kanal Alt Fırsatları: {len(self.channel_opportunities)}")
        print(f"{Fore.RED}   Breakout Adayları: {len(self.breakout_candidates)}")
        print(f"{Fore.BLUE}   İdeal Pearson Sayısı: {len(self.ideal_pearson)}")

        # En yüksek Pearson değerleri
        if self.all_results:
            high_pearson = [r for r in self.all_results if abs(r.get('Pearson', 0)) >= 0.9]
            print(f"{Fore.GREEN}  ⭐ Yüksek Pearson (>=0.9): {len(high_pearson)}")

    def save_failed_list(self, filename="basarisiz_regresyon_dosyalari.txt"):
        """Başarısız dosyaları kaydetme"""
        if self.failed_files:
            try:
                with open(filename, 'w', encoding='utf-8') as f:
                    f.write("# Başarısız Lineer Regresyon analizi dosyaları\n")
                    f.write(f"# Tarih: {datetime.now().strftime('%Y-%m-%d')}\n\n")
                    for file_name in self.failed_files:
                        f.write(f"{file_name}\n")
                print(f"{Fore.YELLOW} Başarısız dosyalar {filename} dosyasına kaydedildi.")
            except Exception as e:
                print(f"{Fore.RED}❌ Başarısız dosya listesi kaydetme hatası: {e}")

    def main(self):
        """Ana fonksiyon"""
        print(f"{Fore.CYAN} Lineer Regresyon ve Pearson Analizi Başlatılıyor...")
        print(f"{Fore.BLUE} Analiz Periyotları: {', '.join(map(str, self.pearson_periods))}")
        print(f"{Fore.BLUE} Özel Analiz Periyotları: {', '.join(map(str, self.analysis_periods))}")

        # Giriş dosyalarını bulma
        input_files = self.find_input_files()

        if not input_files:
            return

        print(f"{Fore.BLUE} Toplam işlenecek dosya: {len(input_files)}\n")

        # Dosyaları işleme
        for i, file_path in enumerate(input_files, 1):
            print(f"\n{Fore.MAGENTA}[{i}/{len(input_files)}] İşleniyor...")
            self.process_single_file(file_path)

        # EMA verilerini birleştirme
        self.merge_ema_data()

        # İstatistikleri hesaplama
        self.calculate_statistics()

        # Sonuçları kaydetme
        success = self.save_results()

        if success:
            self.print_summary()

        # Başarısız dosyaları kaydetme
        self.save_failed_list()

        print(f"\n{Fore.GREEN} Lineer regresyon analizi tamamlandı!")
        print(f"{Fore.BLUE} Ana dosya: StokData/lineer_regresyon_analiz.xlsx")
        print(f"{Fore.BLUE} Arşiv klasörü: StokData/LinearRegression/")


# Kullanım
if __name__ == "__main__":
    analyzer = LinearRegressionAnalyzer()
    analyzer.main()

 

Page 1 of 2712345...1020...»Last »
Etiketler
Teknik AnalizaşkPythonhisse senedi analiziEma AlignmentÜstel Hareketli OrtalamaPine Scripthayatalgoritmik tradingtrend analizipivotEmaallahteratrend takibiyatırım stratejisiBorsaPinotomatik analizpiyasa momentumuyatırım stratejileriborsa eğitimifinansal analizborsa stratejileriborsaPython ile BIST verisi çekmePython teknik analizPython borsa analiziPearson korelasyonuStop-Lossİdeal EmadirençdestekFibonacciİdeal Ema UpTrading ViewCem Sultansonbaharmuhsin yazıcıoğlukehanetözlemhayalmasalatatürkfiravunPhp Melody
Arşiv
  • Ekim 2026
  • Eylül 2026
  • Nisan 2026
  • Ağustos 2025
  • Temmuz 2025
  • Nisan 2025
  • Şubat 2025
  • Ocak 2025
  • Kasım 2024
  • Ekim 2024
  • Temmuz 2024
  • Mart 2024
  • Ocak 2023
  • Ağustos 2018
  • Temmuz 2016
  • Kasım 2015
  • Kasım 2014
  • Aralık 2013
  • Eylül 2013
  • Kasım 2012
  • Ekim 2012
  • Haziran 2011
  • Mart 2011
  • Şubat 2011
  • Ocak 2011
  • Aralık 2010
  • Kasım 2010
  • Eylül 2010
  • Ağustos 2010
  • Temmuz 2010
  • Haziran 2010
  • Mayıs 2010
  • Nisan 2010
  • Mart 2010
  • Şubat 2010
  • Ocak 2010
  • Aralık 2009
  • Kasım 2009
  • Ekim 2009
  • Eylül 2009
  • Ağustos 2009
  • Temmuz 2009
  • Haziran 2009
  • Mayıs 2009
  • Nisan 2009
  • Mart 2009
  • Şubat 2009
  • Ocak 2009
  • Aralık 2008
  • Kasım 2008
Sponsor Bağlantılar
Kategoriler
  • Anlık Tepkiler
  • Bilinçaltı Sayıklamaları
  • Bitmeyen Senfoni
  • Blog
  • Borsa
  • BorsaPin
  • Bu nedir ?
  • Code is prority
  • Halet-i Ruhiye
  • İndikatör
  • Karma Karışık
  • Pine Script
  • Python
  • Teknik Analiz
  • Teknoloji
  • Trading View
  • Wordpress
  • Telegram
  • YouTube
Son Yorumlar
  • Ekrandaki Milyonluk Hacimler Gerçek mi, Yoksa Kurgu mu? için Wizkid
  • Borsada Takas Hareketlerini Okumak: Görünen Alıcı, Gerçek Maliyet ve Tahta Kontrolü için WizkidLagos
  • Fonlarda Finansal Mühendislik, Sistemik Risk ve BIST 30 için Lagosbombai
  • PHP Mobil Cihazları yönlendirme için Azmi Güneş
  • Son bir hatıra için sdc


Borsapin Proje Google Drive

Sponsor Bağlantılar
Sponsor Bağlantılar
.

.

.

.

2026 © SDC