forked from sheetjs/docs.sheetjs.com
		
	
		
			
				
	
	
		
			69 lines
		
	
	
		
			2.3 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
			
		
		
	
	
			69 lines
		
	
	
		
			2.3 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
	
	
| const XLSX = require('xlsx');
 | |
| const tf = require("@tensorflow/tfjs");
 | |
| //const tf = require("@tensorflow/tfjs-node");
 | |
| 
 | |
| function worksheet_to_csv_url(worksheet) {
 | |
|   /* generate CSV */
 | |
|   const csv = XLSX.utils.sheet_to_csv(worksheet);
 | |
| 
 | |
|   /* CSV -> Uint8Array -> Blob */
 | |
|   const u8 = new TextEncoder().encode(csv);
 | |
|   const blob = new Blob([u8], { type: "text/csv" });
 | |
| 
 | |
|   /* generate a blob URL */
 | |
|   return URL.createObjectURL(blob);
 | |
| }
 | |
| 
 | |
| (async() => { try {
 | |
|   /* fetch file */
 | |
|   const f = await fetch("https://docs.sheetjs.com/cd.xls");
 | |
|   const ab = await f.arrayBuffer();
 | |
|   /* parse file and get first worksheet */
 | |
|   const wb = XLSX.read(ab);
 | |
|   const ws = wb.Sheets[wb.SheetNames[0]];
 | |
| 
 | |
|   /* generate blob URL */
 | |
|   const url = worksheet_to_csv_url(ws);
 | |
| 
 | |
|   /* feed to tf.js */
 | |
|   const dataset = tf.data.csv(url, {
 | |
|     hasHeader: true,
 | |
|     configuredColumnsOnly: true,
 | |
|     columnConfigs:{
 | |
|       "Horsepower": {required: false, default: 0},
 | |
|       "Miles_per_Gallon":{required: false, default: 0, isLabel:true}
 | |
|     }
 | |
|   });
 | |
| 
 | |
|   /* pre-process data */
 | |
|   let flat = dataset
 | |
|     .map(({xs,ys}) =>({xs: Object.values(xs), ys: Object.values(ys)}))
 | |
|     .filter(({xs,ys}) => [...xs,...ys].every(v => v>0));
 | |
| 
 | |
|   /* normalize manually :( */
 | |
|   let minX = Infinity, maxX = -Infinity, minY = Infinity, maxY = -Infinity;
 | |
|   await flat.forEachAsync(({xs, ys}) => {
 | |
|     minX = Math.min(minX, xs[0]); maxX = Math.max(maxX, xs[0]);
 | |
|     minY = Math.min(minY, ys[0]); maxY = Math.max(maxY, ys[0]);
 | |
|   });
 | |
|   flat = flat.map(({xs, ys}) => ({xs:xs.map(v => (v-minX)/(maxX - minX)),ys:ys.map(v => (v-minY)/(maxY-minY))}));
 | |
|   flat = flat.batch(32);
 | |
| 
 | |
|   /* build and train model */
 | |
|   const model = tf.sequential();
 | |
|   model.add(tf.layers.dense({inputShape: [1], units: 1}));
 | |
|   model.compile({ optimizer: tf.train.sgd(0.000001), loss: 'meanSquaredError' });
 | |
|   await model.fitDataset(flat, { epochs: 100, callbacks: { onEpochEnd: async (epoch, logs) => {
 | |
|     console.error(`${epoch}:${logs.loss}`);
 | |
|   }}});
 | |
| 
 | |
|   /* predict values */
 | |
|   const inp = tf.linspace(0, 1, 9);
 | |
|   const pred = model.predict(inp);
 | |
|   const xs = await inp.dataSync(), ys = await pred.dataSync();
 | |
| 
 | |
|   for (let i=0; i<xs.length; ++i) {
 | |
|     console.log([xs[i] * (maxX - minX) + minX, ys[i] * (maxY - minY) + minY].join(" "));
 | |
|   }
 | |
| } catch(e) { console.error(`ERROR: ${String(e)}`); }})();
 |