Kas mere tase tõuseb globaalse soojenemise tõttu?


Senini pole selles küsimuses veel täit üksmeelt, kuid me võime võrrelda mere keskmise taseme väärtusi. Mere keskmine tase arvutatakse kui maakera ideaalkuju geoidi antud punkti kõrguse ja mõõtmistulemusel saadud väärtuse vahe; paljudes mõõtmispuunktides on salvestatud mere taseme keskmine väärtus rohkem kui saja aasta jooksul. Nend andmete väärtused võivad tunduda imelikud, näiteks Helsingi andmed algavad

 1879;  7254;N;000
 1880;  7298;N;000
 1881;  7268;N;000
 1882;  7255;N;000
 1883;  7244;N;000
 ...
Siin teine number näitab keskmise meretaseme väärtust sellel aastal; need numbrid algavad kõik seitsmega, sest andmeid selgitav abitekst ütleb, et
" datum at each station is defined to be approximately 7000mm below mean sea level, with this arbitrary choice made many years ago in order to avoid negative numbers in the resulting RLR monthly and annual mean values", seega kõik väärtused algavad seitsmega.

Sellist andmeformaati peab Javascriptis kasutamiseks veidi muutma; seda saab teha Notepad++-i "Otsi/asenda" funktsioonidega.

Et sellises formaadis tabelist saada Javascriptiandmeobjekti, eemaldame kõigepealt mittevajalikud stringid ";N;000" (see string on parem võtta otse failist copy-paste abil):

Search Find ;N;000
Replace with 

Saadud faili peab igaks juhuks ka visuaalselt skaneerima - mõnes reas võib veelgi olla mittevajalikke sümboleid, näit Y;000.

Nüüd asendame semikoolonid ; koolonitega : , sest Javascripti objekt on paar attribuut:väärtus ja asendame reavahetused \n komaga , (siin tuleb kasutada laiendatud vahetust - Extended (\n,\r...)... ) ja võtame kogu saadud rea figuursulgudesse {..} - see on Javascripti objekti süntaksi tunnus. Moodustame üldisema objekti, mis sisaldab nii koha kui ka meretaseme infot ja lisame selle algusesse javascripti muutuja definitsiooni

var data={koht:"Helsinki",andmed:{1879: 7254, ...,2012:7020}}

Salvestame saadud andmemassiivi nimega data.js.

Andmeobjektis võib kasutada ka erinevat formaati, näiteks teha iga aasta alamobjektiks:

{{1879:  7254},{ 1880:  7298},{ 1881:  7268},...}
, kuid kõik andmed ühe andmeobjekti alamobjektidebna
{1879:  7254, 1880:  7298,...,,2012:7020}

on lihtsam ja lihtsam on alati parem - vähem võimaslusi vigadeks.

Selliselt defineeritud andmeobjekti (sisaldab infot koha kohta ja mõõtmisseeriast saab mõõtmiste algus- ja lõpuaasta) saab kasutada graafikule allkirja moodustamiseks, sellepärast vormistame html-lehel kanvaa kahe div-i abil: välimise abil saab määrata kanvaa asukoha lehel, sisemine (div inf kanvaa all) esitab graafiku allkirja, näiteks siin

<div  class="pilt_paremal"> 
    <canvas id="canvas" width="500" height="300"></canvas>
    <div id="inf"></div>
</div>

Nii vormistatud lehte saab kasutada ükskõik millise koha (mõõtmispunkti) merepinna taseme andmete visualiseerimiseks, kui andmed on vormistatud nagu ülal - need sisaldavad ka koha infot..

Impordime html5-faili peas selle andmefaili (andmed peavad juba olemas olema enne graafiku joonistamise skripti!) ja värvime kanvaa tausta õrnalt sinakaks (siis on see html-lehel kohe näha ja seostub teemaga):

<style>
		canvas{
		background-color:#fdfdff;}
	</style>
	<script src="js/data.js"> </script> 

Kogu graafikut joonistav programm on funktsioonis draw() , mis käivitatakse html5-lehe keha (body) laadimisel:

  <body onload="draw();">

Funktsioon draw algab kanvaa leidmise, joonistamiskonteksti ctx loomise, kanvaa mõõtmete salvestamisega muutujates w,h ja andmetest võtmeväljade massiivi keys moodustamisega; testimiseks laseme need väärtused ka konsoolile (ilmub brauserites - Firefox, Chrome) IE F12 vajutamisel:

function draw(){
	var canvas = document.getElementById("canvas");  
	if (canvas.getContext) {  
		var ctx = canvas.getContext("2d"); }
	else
		alert("This browser does not recognize canvas - update your browser!");
	var w = canvas.width;
	var h = canvas.height;
	var keys = Object.keys(data.andmed); //array: [1879,1880,...]
	var n = keys.length; //kui palju on andmeid
	console.log(w,h,n,keys[0]);
  }

Graafiku telgede joonistamisel jätame selle ümber vaba ruumi, selle laius-kõrgus on määratud muutujatega xPadding, yPadding. Täiendame funktsiooni draw() telgede joonistamisega

	var xPadding = 40; //vaba ala x-telje suunas
    var yPadding = 40;  //vaba ala y-telje suunas
	ctx.strokeStyle = '#333'; //r=g=b - tume (3) hall
	ctx.beginPath();
	ctx.moveTo(xPadding, yPadding);
	ctx.lineTo(xPadding, h - yPadding); // vahe ääreni
	ctx.lineTo(canvas.width-xPadding, h - yPadding);
	ctx.stroke(); //teeb jooned nähtavaks

Paigutame graafiku nii, et see maksimaalselt täidab telgedega piiratud ala, selleks peab leidma nii argumendi väärtuste (siin massiiv keys) kui ka funktsiooni väärtuste minimaalsed ja maksimaalsed väärtused. Funktsioon getMaxMin() on kirjeldatud nii, et see kohe ka käivitatakse:

	var minX = 100000, minY = 100000; // kindlasti suurem !
	var  maxX = 0,  maxY = 0;  // kindlasti väiksem!
	(function getMaxMin(){
	// get max min values
	for(var i = 0; i < n; i++){
		if (keys[i] < minX)
			minX = keys[i];
		if (data.andmed[keys[i]] < minY)
			minY = data.andmed[keys[i]];
		if (keys[i] > maxX)
			maxX = keys[i];
		if (data.andmed[keys[i]] > maxY)
			maxY = data.andmed[keys[i]];
	}})();
	console.log(minX,maxX,minY,maxY);

Et Y minimaalne ja maksimaalne väärtus lõpeks 00-ga, teisendame neid veidi:

//teisendame minY, maxY nii, et nende lõpus oleks 00
	minY = minY - (minY%100);
	maxY = maxY + (100 - maxY%100);
	console.log(minY,maxY);

Argumendi ja funktsiooni väärtuste graafikule kandmiseks on tarvis funktsioone, mis skaleerivad väärtuse pikslite asukohaks:

	function getXPixel(val) {
		return (((w - 2*xPadding) / n) * (val - minX) + xPadding);
	}
	function getYPixel(val) {
		return (((h - 2*yPadding) / (maxY - minY)) * ( maxY - val) + yPadding);
	}

Kanname X-teljele argumendi minimaalse ja maksimaalse väärtuse, nende vahele 50-nega jaguvad väärtused ja joonistame graafiku:

	//kanname X-teljele mõned väärtused
	ctx.fillText = 'center';
	ctx.fillText(keys[0], getXPixel(keys[0]), h - yPadding/2 ); // algus 
	for(var i = 0; i < n; i ++) {
	if (keys[i]%50 == 0) //kanname X-telejele vaid 50-ga jaguvad aastad
		ctx.fillText(keys[i], getXPixel(keys[i]), h - yPadding/2 );
	}
	ctx.fillText(keys[n-1], getXPixel(keys[n-1]), h - yPadding/2 );
  

Y-teljele kanname kõik 'ümmargused', s.t. 00-ga lõppevad väärtused. Nende leidmiseks ei saa kasutada moodulit, sest y väärtused on reaalarvud ja mooduli järgi võrdelmisel ei saa täpset väärtust, mida saaks võrrelda, sellepärast kasutame while-tsüklit:

var Y = minY;
	ctx.textAlign = 'right';
	while(Y <= maxY)
		{ ctx.fillText(Y, xPadding, getYPixel(Y));
		Y += 100;}

Jääb üle vaid graafiku joonistamine:

 
	//joonistame graafiku
	ctx.strokeStyle = '#33f'; //  tume sinine
	ctx.beginPath();
	ctx.moveTo(getXPixel(keys[0]), getYPixel(data.andmed[keys[0]]));
	for(var i = 1; i < n; i ++) {
		ctx.lineTo(getXPixel(keys[i]), getYPixel(data.andmed[keys[i]]));
	}
	ctx.stroke();

Lisame graafikule ka allkirja:

  var inf = document.getElementById("inf");  //info esitamiseks
  inf.innerHTML="Merepinna kõrgus, koht: "+data.koht+", aastad : "+minX+".."+maxX;

Saadud ülespoole liikuv murdjoon siiski ei tõesta, et maailmamere tase kliima soojenemise tõttu tõuseb. Mõõteperiood on Maa eaga võrreldes kaduvväike (Lippmaa: "me väljume praegu viimasest jääajast,, aga üle 20000 aasta see ei kesta ja uus jääaeg tuleb nagunii"), maakera kuju pole staatiline, maakera on ju sula palli peal ujuv hangunud koorik ja selle kuju muutub kogu aeg ja kogu meie planeeti mõjutab inimeste (lokalne) tegutsemine vähem kui globaalsed protsessid, näiteks Päikese l toimuvad, seega akadeemik Lippmaal võib olla õigus, kui ta eitab kliima soojenemist.

Ülesadeid

1. Kuigi andmete väärtus on nihutatud (~7m), peaks muutuse suuruse hindamiseks ka Y-teljel midagi olema - lisa Y-teljele väärtused, lugedes 0-punktiks (näiteks) mõõtmiste seeria esimest väärtust (kindlasti peaks olema näha ka ühik).