version bump 0.12.8: sheetRows multiformat support

- all formats accept `sheetRows` option (fixes #1062 h/t @prog666)
- `table_to_*` support for `sheetRows`
- demo cleanup
This commit is contained in:
SheetJS 2018-04-06 02:39:48 -04:00
parent 3592efa77b
commit 93f7749bec
37 changed files with 728 additions and 135 deletions

@ -107,6 +107,12 @@ AngularJS
NativeScript
angular-cli
- demos/array/README.md
WebGL
WebAssembly
dataset
TensorFlow
- demos/database/README.md
Knex
LowDB

@ -198,6 +198,7 @@ The [`demos` directory](demos/) includes sample projects for:
- [`XMLHttpRequest and fetch`](demos/xhr/)
- [`nodejs server`](demos/server/)
- [`databases and key/value stores`](demos/database/)
- [`typed arrays and math`](demos/array/)
**Bundlers and Tooling**
- [`browserify`](demos/browserify/)
@ -2045,9 +2046,10 @@ Both functions accept options arguments:
| Option Name | Default | Description |
| :---------- | :------: | :-------------------------------------------------- |
|`raw` | | If true, every cell will hold raw strings |
|`dateNF` | FMT 14 | Use specified date format in string output |
|`cellDates` | false | Store dates as type `d` (default is `n`) |
|`raw` | | If true, every cell will hold raw strings |
|`sheetRows` | 0 | If >0, read the first `sheetRows` rows of the table |
<details>

@ -1 +1 @@
XLSX.version = '0.12.7';
XLSX.version = '0.12.8';

@ -180,6 +180,7 @@ function dbf_to_aoa(buf, opts)/*:AOA*/ {
}
}
if(ft != 0x02) if(d.l < d.length && d[d.l++] != 0x1A) throw new Error("DBF EOF Marker missing " + (d.l-1) + " of " + d.length + " " + d[d.l-1].toString(16));
if(opts && opts.sheetRows) out = out.slice(0, opts.sheetRows);
return out;
}
@ -206,7 +207,8 @@ function sheet_to_dbf(ws/*:Worksheet*/, opts/*:WriteOpts*/) {
for(i = 0; i < headers.length; ++i) {
if(i == null) continue;
++hcnt;
if(typeof headers[i] !== 'string') throw new Error("DBF Invalid column name");
if(typeof headers[i] === 'number') headers[i] = headers[i].toString(10);
if(typeof headers[i] !== 'string') throw new Error("DBF Invalid column name " + headers[i] + " |" + (typeof headers[i]) + "|");
if(headers.indexOf(headers[i]) !== i) for(j=0; j<1024;++j)
if(headers.indexOf(headers[i] + "_" + j) == -1) { headers[i] += "_" + j; break; }
}
@ -394,6 +396,7 @@ var SYLK = (function() {
}
if(rowinfo.length > 0) sht['!rows'] = rowinfo;
if(colinfo.length > 0) sht['!cols'] = colinfo;
if(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);
return [arr, sht];
}
@ -484,7 +487,7 @@ var DIF = (function() {
}
throw new Error("Unrecognized type " + opts.type);
}
function dif_to_aoa_str(str/*:string*//*::, opts*/)/*:AOA*/ {
function dif_to_aoa_str(str/*:string*/, opts)/*:AOA*/ {
var records = str.split('\n'), R = -1, C = -1, ri = 0, arr/*:AOA*/ = [];
for (; ri !== records.length; ++ri) {
if (records[ri].trim() === 'BOT') { arr[++R] = []; C = 0; continue; }
@ -512,6 +515,7 @@ var DIF = (function() {
}
if (data === 'EOD') break;
}
if(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);
return arr;
}
@ -585,7 +589,7 @@ var ETH = (function() {
function decode(s/*:string*/)/*:string*/ { return s.replace(/\\b/g,"\\").replace(/\\c/g,":").replace(/\\n/g,"\n"); }
function encode(s/*:string*/)/*:string*/ { return s.replace(/\\/g, "\\b").replace(/:/g, "\\c").replace(/\n/g,"\\n"); }
function eth_to_aoa(str/*:string*//*::, opts*/)/*:AOA*/ {
function eth_to_aoa(str/*:string*/, opts)/*:AOA*/ {
var records = str.split('\n'), R = -1, C = -1, ri = 0, arr/*:AOA*/ = [];
for (; ri !== records.length; ++ri) {
var record = records[ri].trim().split(":");
@ -606,6 +610,7 @@ var ETH = (function() {
if(record[2] == 'vtf') arr[R][C] = [arr[R][C], _f];
}
}
if(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);
return arr;
}
@ -713,6 +718,7 @@ var PRN = (function() {
for(C = 1; C <= (lines[R].length - start)/10 + 1; ++C)
set_text_arr(lines[R].slice(start+(C-1)*10,start+C*10).trim(),arr,R,C,o);
}
if(o.sheetRows) arr = arr.slice(0, o.sheetRows);
return arr;
}
@ -799,11 +805,11 @@ var PRN = (function() {
start = end+1;
if(range.e.c < C) range.e.c = C;
if(range.e.r < R) range.e.r = R;
if(cc == sepcc) ++C; else { C = 0; ++R; }
if(cc == sepcc) ++C; else { C = 0; ++R; if(o.sheetRows && o.sheetRows <= R) return true; }
}
for(;end < str.length;++end) switch((cc=str.charCodeAt(end))) {
outer: for(;end < str.length;++end) switch((cc=str.charCodeAt(end))) {
case 0x22: instr = !instr; break;
case sepcc: case 0x0a: case 0x0d: if(!instr) finish_cell(); break;
case sepcc: case 0x0a: case 0x0d: if(!instr && finish_cell()) break outer; break;
default: break;
}
if(end - start > 0) finish_cell();

@ -24,7 +24,7 @@ var WK_ = (function() {
throw "Unsupported type " + opts.type;
}
function lotus_to_workbook_buf(d,opts)/*:Workbook*/ {
function lotus_to_workbook_buf(d, opts)/*:Workbook*/ {
if(!d) return d;
var o = opts || {};
if(DENSE != null && o.dense == null) o.dense = DENSE;
@ -32,6 +32,7 @@ var WK_ = (function() {
var sheets = {}, snames = [n];
var refguess = {s: {r:0, c:0}, e: {r:0, c:0} };
var sheetRows = o.sheetRows || 0;
if(d[2] == 0x02) o.Enum = WK1Enum;
else if(d[2] == 0x1a) o.Enum = WK3Enum;
@ -79,6 +80,7 @@ var WK_ = (function() {
sidx = val[3]; n = "Sheet" + (sidx + 1);
snames.push(n);
}
if(sheetRows > 0 && val[0].r >= sheetRows) break;
if(o.dense) {
if(!s[val[0].r]) s[val[0].r] = [];
s[val[0].r][val[0].c] = val[1];

@ -75,7 +75,7 @@ function parse_ws_xml(data/*:?string*/, opts, idx/*:number*/, rels, wb/*:WBWBPro
if(!s["!ref"] && refguess.e.c >= refguess.s.c && refguess.e.r >= refguess.s.r) s["!ref"] = encode_range(refguess);
if(opts.sheetRows > 0 && s["!ref"]) {
var tmpref = safe_decode_range(s["!ref"]);
if(opts.sheetRows < +tmpref.e.r) {
if(opts.sheetRows <= +tmpref.e.r) {
tmpref.e.r = opts.sheetRows - 1;
if(tmpref.e.r > refguess.e.r) tmpref.e.r = refguess.e.r;
if(tmpref.e.r < tmpref.s.r) tmpref.s.r = tmpref.e.r;

@ -645,7 +645,7 @@ function parse_ws_bin(data, _opts, idx, rels, wb/*:WBWBProps*/, themes, styles)/
if(!s["!ref"] && (refguess.s.r < 2000000 || ref && (ref.e.r > 0 || ref.e.c > 0 || ref.s.r > 0 || ref.s.c > 0))) s["!ref"] = encode_range(ref || refguess);
if(opts.sheetRows && s["!ref"]) {
var tmpref = safe_decode_range(s["!ref"]);
if(opts.sheetRows < +tmpref.e.r) {
if(opts.sheetRows <= +tmpref.e.r) {
tmpref.e.r = opts.sheetRows - 1;
if(tmpref.e.r > refguess.e.r) tmpref.e.r = refguess.e.r;
if(tmpref.e.r < tmpref.s.r) tmpref.s.r = tmpref.e.r;

@ -276,7 +276,14 @@ function parse_xlml_xml(d, _opts)/*:Workbook*/ {
if(Rn[1]==='/'){
if((tmp=state.pop())[0]!==Rn[3]) throw new Error("Bad state: "+tmp.join("|"));
sheetnames.push(sheetname);
if(refguess.s.r <= refguess.e.r && refguess.s.c <= refguess.e.c) cursheet["!ref"] = encode_range(refguess);
if(refguess.s.r <= refguess.e.r && refguess.s.c <= refguess.e.c) {
cursheet["!ref"] = encode_range(refguess);
if(opts.sheetRows && opts.sheetRows <= refguess.e.r) {
cursheet["!fullref"] = cursheet["!ref"];
refguess.e.r = opts.sheetRows - 1;
cursheet["!ref"] = encode_range(refguess);
}
}
if(merges.length) cursheet["!merges"] = merges;
if(cstys.length > 0) cursheet["!cols"] = cstys;
if(rowinfo.length > 0) cursheet["!rows"] = rowinfo;

@ -129,6 +129,7 @@ function parse_workbook(blob, options/*:ParseOpts*/)/*:Workbook*/ {
};
var addcell = function addcell(cell/*:any*/, line/*:any*/, options/*:any*/) {
if(file_depth > 1) return;
if(options.sheetRows && cell.r >= options.sheetRows) cell_valid = false;
if(!cell_valid) return;
if(options.cellStyles && line.XF && line.XF.data) process_cell_style(cell, line, options);
delete line.ixfe; delete line.XF;
@ -152,8 +153,7 @@ function parse_workbook(blob, options/*:ParseOpts*/)/*:Workbook*/ {
break;
}
}
if(options.sheetRows && lastcell.r >= options.sheetRows) cell_valid = false;
else {
{
if(options.dense) {
if(!out[cell.r]) out[cell.r] = [];
out[cell.r][cell.c] = line;
@ -319,6 +319,13 @@ function parse_workbook(blob, options/*:ParseOpts*/)/*:Workbook*/ {
if(range.e.r > 0 && range.e.c > 0) {
range.e.r--; range.e.c--;
out["!ref"] = encode_range(range);
if(options.sheetRows && options.sheetRows <= range.e.r) {
var tmpri = range.e.r;
range.e.r = options.sheetRows - 1;
out["!fullref"] = out["!ref"];
out["!ref"] = encode_range(range);
range.e.r = tmpri;
}
range.e.r++; range.e.c++;
}
if(merges.length > 0) out["!merges"] = merges;

@ -15,7 +15,7 @@ var HTML_ = (function() {
for(i = 0; i < rows.length; ++i) {
var row = rows[i].trim();
var hd = row.slice(0,3).toLowerCase();
if(hd == "<tr") { ++R; C = 0; continue; }
if(hd == "<tr") { ++R; if(opts.sheetRows && opts.sheetRows <= R) { --R; break; } C = 0; continue; }
if(hd != "<td") continue;
var cells = row.split(/<\/td>/i);
for(j = 0; j < cells.length; ++j) {
@ -119,10 +119,11 @@ function parse_dom_table(table/*:HTMLElement*/, _opts/*:?any*/)/*:Worksheet*/ {
if(DENSE != null) opts.dense = DENSE;
var ws/*:Worksheet*/ = opts.dense ? ([]/*:any*/) : ({}/*:any*/);
var rows/*:HTMLCollection<HTMLTableRowElement>*/ = table.getElementsByTagName('tr');
var range/*:Range*/ = {s:{r:0,c:0},e:{r:rows.length - 1,c:0}};
var sheetRows = Math.min(opts.sheetRows||10000000, rows.length);
var range/*:Range*/ = {s:{r:0,c:0},e:{r:sheetRows - 1,c:0}};
var merges/*:Array<Range>*/ = [], midx = 0;
var R = 0, _C = 0, C = 0, RS = 0, CS = 0;
for(; R < rows.length; ++R) {
for(; R < sheetRows; ++R) {
var row/*:HTMLTableRowElement*/ = rows[R];
var elts/*:HTMLCollection<HTMLTableCellElement>*/ = (row.children/*:any*/);
for(_C = C = 0; _C < elts.length; ++_C) {
@ -156,6 +157,7 @@ function parse_dom_table(table/*:HTMLElement*/, _opts/*:?any*/)/*:Worksheet*/ {
}
ws['!merges'] = merges;
ws['!ref'] = encode_range(range);
if(sheetRows < rows.length) ws['!fullref'] = encode_range((range.e.r = rows.length-1,range));
return ws;
}

@ -62,6 +62,11 @@ var parse_content_xml = (function() {
case 'table': case '工作表': // 9.1.2 <table:table>
if(Rn[1]==='/') {
if(range.e.c >= range.s.c && range.e.r >= range.s.r) ws['!ref'] = encode_range(range);
if(opts.sheetRows > 0 && opts.sheetRows <= range.e.r) {
ws['!fullref'] = ws['!ref'];
range.e.r = opts.sheetRows - 1;
ws['!ref'] = encode_range(range);
}
if(merges.length) ws['!merges'] = merges;
if(rowinfo.length) ws["!rows"] = rowinfo;
sheetag.name = utf8read(sheetag['名称'] || sheetag.name);
@ -178,7 +183,7 @@ var parse_content_xml = (function() {
if(comments.length > 0) { q.c = comments; comments = []; }
if(textp && opts.cellText !== false) q.w = textp;
if(!isstub || opts.sheetStubs) {
if(!(opts.sheetRows && opts.sheetRows < R)) {
if(!(opts.sheetRows && opts.sheetRows <= R)) {
for(var rpt = 0; rpt < rowpeat; ++rpt) {
colpeat = parseInt(ctag['number-columns-repeated']||"1", 10);
if(opts.dense) {

@ -26,6 +26,7 @@ can be installed with Bash on Windows or with `cygwin`.
- [`XMLHttpRequest and fetch`](xhr/)
- [`nodejs server`](server/)
- [`databases and key/value stores`](database/)
- [`typed arrays and math`](array/)
**Bundlers and Tooling**
- [`browserify`](browserify/)

8
demos/array/Makefile Normal file

@ -0,0 +1,8 @@
.PHONY: tfjs
tfjs:
npm install @tensorflow/tfjs
node tf.js
.PHONY: propel
propel:
node propel.js

155
demos/array/README.md Normal file

@ -0,0 +1,155 @@
# Typed Arrays and Math
ECMAScript version 6 introduced Typed Arrays, array-like objects designed for
low-level optimizations and predictable operations. They are supported in most
modern browsers and form the basis of various APIs, including NodeJS Buffers,
WebGL buffers, WebAssembly, and tensors in linear algebra and math libraries.
This demo covers conversions between worksheets and Typed Arrays. It also tries
to cover common numerical libraries that work with data arrays.
Excel supports a subset of the IEEE754 Double precision floating point numbers,
but many libraries only support `Float32` Single precision values. `Math.fround`
rounds `Number` values to the nearest single-precision floating point value.
## Working with Data in Typed Arrays
Typed arrays are not true Array objects. The array of array utility functions
like `aoa_to_sheet` will not handle arrays of Typed Arrays.
#### Exporting Typed Arrays to a Worksheet
A single typed array can be converted to a pure JS array with `Array.from`:
```js
var column = Array.from(dataset_typedarray);
```
`aoa_to_sheet` expects a row-major array of arrays. To export multiple data
sets, "transpose" the data:
```js
/* assuming data is an array of typed arrays */
var aoa = [];
for(var i = 0; i < data.length; ++i) {
for(var j = 0; j < data[i].length; ++j) {
if(!aoa[j]) aoa[j] = [];
aoa[j][i] = data[i][j];
}
}
/* aoa can be directly converted to a worksheet object */
var ws = XLSX.utils.aoa_to_sheet(aoa);
```
#### Importing Data from a Spreadsheet
`sheet_to_json` with the option `header:1` will generate a row-major array of
arrays that can be transposed. However, it is more efficient to walk the sheet
manually:
```js
/* find worksheet range */
var range = XLSX.utils.decode_range(ws['!ref']);
var out = []
/* walk the columns */
for(var C = range.s.c; C <= range.e.c; ++C) {
/* create the typed array */
var ta = new Float32Array(range.e.r - range.s.r + 1);
/* walk the rows */
for(var R = range.s.r; R <= range.e.r; ++R) {
/* find the cell, skip it if the cell isn't numeric or boolean */
var cell = ws[XLSX.utils.encode_cell({r:R, c:C})];
if(!cell || cell.t != 'n' && cell.t != 'b') continue;
/* assign to the typed array */
ta[R - range.s.r] = cell.v;
}
out.push(ta);
}
```
If the data set has a header row, the loop can be adjusted to skip those rows.
## Demos
Each example focuses on single-variable linear regression. Sample worksheets
will start with a label row. The first column is the x-value and the second
column is the y-value. A sample spreadsheet can be generated randomly:
```js
var aoo = [];
for(var i = 0; i < 100; ++i) aoo.push({x:i, y:2 * i + Math.random()});
var ws = XLSX.utils.json_to_sheet(aoo);
var wb = XLSX.utils.book_new(); XLSX.utils.book_append_sheet(wb, ws, "Sheet1");
XLSX.writeFile(wb, "linreg.xlsx");
```
Some libraries provide utility functions that work with plain arrays of numbers.
When possible, they should be preferred over manual conversion.
Reshaping raw float arrays and exporting to a worksheet is straightforward:
```js
function array_to_sheet(farray, shape, headers) {
/* generate new AOA from the float array */
var aoa = [];
for(var j = 0; j < shape[0]; ++j) {
aoa[j] = [];
for(var i = 0; i < shape[1]; ++i) aoa[j][i] = farray[j * shape[1] + i];
}
/* add headers and generate worksheet */
if(headers) aoa.unshift(headers);
return XLSX.utils.aoa_to_sheet(aoa);
}
```
#### Tensor Operations with Propel ML
[Propel ML](http://propelml.org/) `tensor` objects can be transposed:
```js
var tensor = pr.tensor(aoa).transpose();
var col1 = tensor.slice(0, 1);
var col2 = tensor.slice(1, 1);
```
To export to a worksheet, `dataSync` generates a `Float32Array` that can be
re-shaped in JS:
```js
/* extract shape and float array */
var tensor = pr.concat([col1, col2]).transpose();
var shape = tensor.shape;
var farray = tensor.dataSync();
var ws = array_to_sheet(farray, shape, ["header1", "header2"]);
```
The demo generates a sample dataset and uses Propel to calculate the OLS linear
regression coefficients. Afterwards, the tensors are exported to a new file.
#### TensorFlow
[TensorFlow](https://js.tensorflow.org/) `tensor` objects can be created from
arrays of arrays:
```js
var tensor = tf.tensor2d(aoa).transpose();
var col1 = tensor.slice([0,0], [1,tensor.shape[1]]).flatten();
var col2 = tensor.slice([1,0], [1,tensor.shape[1]]).flatten();
```
`stack` should be used to create the 2-d tensor for export:
```js
var tensor = tf.stack([col1, col2]).transpose();
var shape = tensor.shape;
var farray = tensor.dataSync();
var ws = array_to_sheet(farray, shape, ["header1", "header2"]);
```
The demo generates a sample dataset and uses a simple linear predictor with
least-squares scoring to calculate regression coefficients. The tensors are
exported to a new file.
[![Analytics](https://ga-beacon.appspot.com/UA-36810333-1/SheetJS/js-xlsx?pixel)](https://github.com/SheetJS/js-xlsx)

27
demos/array/linest.js Normal file

@ -0,0 +1,27 @@
/* xlsx.js (C) 2013-present SheetJS -- http://sheetjs.com */
/*global module, require, XLSX:true */
if(typeof require !== 'undefined' && typeof XLSX === 'undefined') XLSX = require('xlsx');
function generate_random_file(n) {
if(!n) n = 100;
var aoo = [];
var x_ = 0, y_ = 0, xx = 0, xy = 0;
for(var i = 0; i < n; ++i) {
var y = Math.fround(2 * i + Math.random());
aoo.push({x:i, y:y});
x_ += i / n; y_ += y / n; xx += i*i; xy += i * y;
}
var m = Math.fround((xy - n * x_ * y_)/(xx - n * x_ * x_));
console.log(m, Math.fround(y_ - m * x_), "JS Pre");
var ws = XLSX.utils.json_to_sheet(aoo);
var wb = XLSX.utils.book_new();
XLSX.utils.book_append_sheet(wb, ws, "Sheet1");
ws = XLSX.utils.aoa_to_sheet([[2, 0]]);
XLSX.utils.sheet_set_array_formula(ws, "A1:B1", "LINEST(Sheet1!B2:B101,Sheet1!A2:A101)");
XLSX.utils.book_append_sheet(wb, ws, "Sheet2");
XLSX.writeFile(wb, "linreg.xlsx");
}
if(typeof module !== 'undefined') module.exports = {
generate_random_file: generate_random_file
};

59
demos/array/propel.js Normal file

@ -0,0 +1,59 @@
/* xlsx.js (C) 2013-present SheetJS -- http://sheetjs.com */
/* eslint-env node */
var XLSX = require('xlsx');
var pr = require('propel');
var linest = require('./linest');
/* generate linreg.xlsx with 100 random points */
linest.generate_random_file(100);
/* get the first worksheet as an array of arrays, skip the first row */
var wb = XLSX.readFile('linreg.xlsx');
var ws = wb.Sheets[wb.SheetNames[0]];
var aoa = XLSX.utils.sheet_to_json(ws, {header:1, raw:true}).slice(1);
/* calculate the coefficients in JS */
(function(aoa) {
var x_ = 0, y_ = 0, xx = 0, xy = 0, n = aoa.length;
for(var i = 0; i < n; ++i) {
x_ += aoa[i][0] / n;
y_ += aoa[i][1] / n;
xx += aoa[i][0] * aoa[i][0];
xy += aoa[i][0] * aoa[i][1];
}
var m = Math.fround((xy - n * x_ * y_)/(xx - n * x_ * x_));
console.log(m, Math.fround(y_ - m * x_), "JS Post");
})(aoa);
/* build X and Y vectors */
var tensor = pr.tensor(aoa).transpose();
var xs = tensor.slice(0, 1);
var ys = tensor.slice(1, 1);
/* compute the coefficient */
var n = xs.size;
var x_ = Math.fround(xs.reduceMean().dataSync()[0]);
var y_ = Math.fround(ys.reduceMean().dataSync()[0]);
var xx = Math.fround(xs.dot(xs.transpose()).dataSync()[0]);
var xy = Math.fround(xs.dot(ys.transpose()).dataSync()[0]);
var m = Math.fround((xy - n * x_ * y_)/(xx - n * x_ * x_));
var b_ = Math.fround(y_ - m * x_);
console.log(m, b_, "Propel");
var yh = xs.mul(m).add(b_);
/* export data to aoa */
var prdata = pr.concat([xs, ys, yh]).transpose();
var shape = prdata.shape;
var prarr = prdata.dataSync();
var praoa = [];
for(var j = 0; j < shape[0]; ++j) {
praoa[j] = [];
for(var i = 0; i < shape[1]; ++i) praoa[j][i] = prarr[j * shape[1] + i];
}
/* add headers and export */
praoa.unshift(["x", "y", "pred"]);
var new_ws = XLSX.utils.aoa_to_sheet(praoa);
var new_wb = XLSX.utils.book_new();
XLSX.utils.book_append_sheet(new_wb, new_ws, "Sheet1");
XLSX.writeFile(new_wb, "propel.xls");

78
demos/array/tf.js Normal file

@ -0,0 +1,78 @@
/* xlsx.js (C) 2013-present SheetJS -- http://sheetjs.com */
/* eslint-env node */
var XLSX = require('xlsx');
var tf = require('@tensorflow/tfjs');
var linest = require('./linest');
/* generate linreg.xlsx with 100 random points */
var N = 100;
linest.generate_random_file(N);
/* get the first worksheet as an array of arrays, skip the first row */
var wb = XLSX.readFile('linreg.xlsx');
var ws = wb.Sheets[wb.SheetNames[0]];
var aoa = XLSX.utils.sheet_to_json(ws, {header:1, raw:true}).slice(1);
/* calculate the coefficients in JS */
(function(aoa) {
var x_ = 0, y_ = 0, xx = 0, xy = 0, n = aoa.length;
for(var i = 0; i < n; ++i) {
x_ += aoa[i][0] / n;
y_ += aoa[i][1] / n;
xx += aoa[i][0] * aoa[i][0];
xy += aoa[i][0] * aoa[i][1];
}
var m = Math.fround((xy - n * x_ * y_)/(xx - n * x_ * x_));
console.log(m, Math.fround(y_ - m * x_), "JS Post");
})(aoa);
/* build X and Y vectors */
var tensor = tf.tensor2d(aoa).transpose();
console.log(tensor.shape);
var xs = tensor.slice([0,0], [1,tensor.shape[1]]).flatten();
var ys = tensor.slice([1,0], [1,tensor.shape[1]]).flatten();
/* set up variables with initial guess */
var x_ = xs.mean().dataSync()[0];
var y_ = ys.mean().dataSync()[0];
var a = tf.variable(tf.scalar(y_/x_));
var b = tf.variable(tf.scalar(Math.random()));
/* linear predictor */
function predict(x) { return tf.tidy(function() { return a.mul(x).add(b); }); }
/* mean square scoring */
function loss(yh, y) { return yh.sub(y).square().mean(); }
/* train */
for(var j = 0; j < 5; ++j) {
var learning_rate = 0.0001 /(j+1), iterations = 1000;
var optimizer = tf.train.sgd(learning_rate);
for(var i = 0; i < iterations; ++i) optimizer.minimize(function() {
var pred = predict(xs);
var L = loss(pred, ys);
return L
});
/* compute the coefficient */
var m = a.dataSync()[0], b_ = b.dataSync()[0];
console.log(m, b_, "TF " + iterations * (j+1));
}
/* export data to aoa */
var yh = predict(xs);
var tfdata = tf.stack([xs, ys, yh]).transpose();
var shape = tfdata.shape;
var tfarr = tfdata.dataSync();
var tfaoa = [];
for(j = 0; j < shape[0]; ++j) {
tfaoa[j] = [];
for(i = 0; i < shape[1]; ++i) tfaoa[j][i] = tfarr[j * shape[1] + i];
}
/* add headers and export */
tfaoa.unshift(["x", "y", "pred"]);
var new_ws = XLSX.utils.aoa_to_sheet(tfaoa);
var new_wb = XLSX.utils.book_new();
XLSX.utils.book_append_sheet(new_wb, new_ws, "Sheet1");
XLSX.writeFile(new_wb, "tfjs.xls");

@ -28,4 +28,4 @@ document.getElementById('sjsdownload').addEventListener('click', function() {
XLSX.utils.book_append_sheet(wb, ws, 'Bookmarks');
XLSX.writeFile(wb, "bookmarks.xlsx");
});
});
});

@ -38,6 +38,6 @@ chrome.runtime.onInstalled.addListener(function() {
});
function sjsexport_cb(wb) {
if(!wb || !wb.SheetNames || !wb.Sheets) { console.log(wb); return alert("Error in exporting table"); }
if(!wb || !wb.SheetNames || !wb.Sheets) { return alert("Error in exporting table"); }
XLSX.writeFile(wb, "export.xlsx");
}
}

30
dist/xlsx.core.min.js generated vendored

File diff suppressed because one or more lines are too long

2
dist/xlsx.core.min.map generated vendored

File diff suppressed because one or more lines are too long

63
dist/xlsx.extendscript.js generated vendored

@ -9141,7 +9141,7 @@ module.exports = ZStream;
/*global global, exports, module, require:false, process:false, Buffer:false, ArrayBuffer:false */
var XLSX = {};
(function make_xlsx(XLSX){
XLSX.version = '0.12.7';
XLSX.version = '0.12.8';
var current_codepage = 1200, current_ansi = 1252;
/*global cptable:true */
if(typeof module !== "undefined" && typeof require !== 'undefined') {
@ -15055,6 +15055,7 @@ var fields = [], field = ({});
}
}
if(ft != 0x02) if(d.l < d.length && d[d.l++] != 0x1A) throw new Error("DBF EOF Marker missing " + (d.l-1) + " of " + d.length + " " + d[d.l-1].toString(16));
if(opts && opts.sheetRows) out = out.slice(0, opts.sheetRows);
return out;
}
@ -15081,7 +15082,8 @@ function sheet_to_dbf(ws, opts) {
for(i = 0; i < headers.length; ++i) {
if(i == null) continue;
++hcnt;
if(typeof headers[i] !== 'string') throw new Error("DBF Invalid column name");
if(typeof headers[i] === 'number') headers[i] = headers[i].toString(10);
if(typeof headers[i] !== 'string') throw new Error("DBF Invalid column name " + headers[i] + " |" + (typeof headers[i]) + "|");
if(headers.indexOf(headers[i]) !== i) for(j=0; j<1024;++j)
if(headers.indexOf(headers[i] + "_" + j) == -1) { headers[i] += "_" + j; break; }
}
@ -15269,6 +15271,7 @@ var SYLK = (function() {
}
if(rowinfo.length > 0) sht['!rows'] = rowinfo;
if(colinfo.length > 0) sht['!cols'] = colinfo;
if(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);
return [arr, sht];
}
@ -15359,7 +15362,7 @@ var DIF = (function() {
}
throw new Error("Unrecognized type " + opts.type);
}
function dif_to_aoa_str(str) {
function dif_to_aoa_str(str, opts) {
var records = str.split('\n'), R = -1, C = -1, ri = 0, arr = [];
for (; ri !== records.length; ++ri) {
if (records[ri].trim() === 'BOT') { arr[++R] = []; C = 0; continue; }
@ -15387,6 +15390,7 @@ var DIF = (function() {
}
if (data === 'EOD') break;
}
if(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);
return arr;
}
@ -15460,7 +15464,7 @@ var ETH = (function() {
function decode(s) { return s.replace(/\\b/g,"\\").replace(/\\c/g,":").replace(/\\n/g,"\n"); }
function encode(s) { return s.replace(/\\/g, "\\b").replace(/:/g, "\\c").replace(/\n/g,"\\n"); }
function eth_to_aoa(str) {
function eth_to_aoa(str, opts) {
var records = str.split('\n'), R = -1, C = -1, ri = 0, arr = [];
for (; ri !== records.length; ++ri) {
var record = records[ri].trim().split(":");
@ -15481,6 +15485,7 @@ var ETH = (function() {
if(record[2] == 'vtf') arr[R][C] = [arr[R][C], _f];
}
}
if(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);
return arr;
}
@ -15588,6 +15593,7 @@ var PRN = (function() {
for(C = 1; C <= (lines[R].length - start)/10 + 1; ++C)
set_text_arr(lines[R].slice(start+(C-1)*10,start+C*10).trim(),arr,R,C,o);
}
if(o.sheetRows) arr = arr.slice(0, o.sheetRows);
return arr;
}
@ -15674,11 +15680,11 @@ var PRN = (function() {
start = end+1;
if(range.e.c < C) range.e.c = C;
if(range.e.r < R) range.e.r = R;
if(cc == sepcc) ++C; else { C = 0; ++R; }
if(cc == sepcc) ++C; else { C = 0; ++R; if(o.sheetRows && o.sheetRows <= R) return true; }
}
for(;end < str.length;++end) switch((cc=str.charCodeAt(end))) {
outer: for(;end < str.length;++end) switch((cc=str.charCodeAt(end))) {
case 0x22: instr = !instr; break;
case sepcc: case 0x0a: case 0x0d: if(!instr) finish_cell(); break;
case sepcc: case 0x0a: case 0x0d: if(!instr && finish_cell()) break outer; break;
default: break;
}
if(end - start > 0) finish_cell();
@ -15777,7 +15783,7 @@ var WK_ = (function() {
throw "Unsupported type " + opts.type;
}
function lotus_to_workbook_buf(d,opts) {
function lotus_to_workbook_buf(d, opts) {
if(!d) return d;
var o = opts || {};
if(DENSE != null && o.dense == null) o.dense = DENSE;
@ -15785,6 +15791,7 @@ var WK_ = (function() {
var sheets = {}, snames = [n];
var refguess = {s: {r:0, c:0}, e: {r:0, c:0} };
var sheetRows = o.sheetRows || 0;
if(d[2] == 0x02) o.Enum = WK1Enum;
else if(d[2] == 0x1a) o.Enum = WK3Enum;
@ -15832,6 +15839,7 @@ var WK_ = (function() {
sidx = val[3]; n = "Sheet" + (sidx + 1);
snames.push(n);
}
if(sheetRows > 0 && val[0].r >= sheetRows) break;
if(o.dense) {
if(!s[val[0].r]) s[val[0].r] = [];
s[val[0].r][val[0].c] = val[1];
@ -21033,7 +21041,7 @@ function parse_ws_xml(data, opts, idx, rels, wb, themes, styles) {
if(!s["!ref"] && refguess.e.c >= refguess.s.c && refguess.e.r >= refguess.s.r) s["!ref"] = encode_range(refguess);
if(opts.sheetRows > 0 && s["!ref"]) {
var tmpref = safe_decode_range(s["!ref"]);
if(opts.sheetRows < +tmpref.e.r) {
if(opts.sheetRows <= +tmpref.e.r) {
tmpref.e.r = opts.sheetRows - 1;
if(tmpref.e.r > refguess.e.r) tmpref.e.r = refguess.e.r;
if(tmpref.e.r < tmpref.s.r) tmpref.s.r = tmpref.e.r;
@ -22181,7 +22189,7 @@ function parse_ws_bin(data, _opts, idx, rels, wb, themes, styles) {
if(!s["!ref"] && (refguess.s.r < 2000000 || ref && (ref.e.r > 0 || ref.e.c > 0 || ref.s.r > 0 || ref.s.c > 0))) s["!ref"] = encode_range(ref || refguess);
if(opts.sheetRows && s["!ref"]) {
var tmpref = safe_decode_range(s["!ref"]);
if(opts.sheetRows < +tmpref.e.r) {
if(opts.sheetRows <= +tmpref.e.r) {
tmpref.e.r = opts.sheetRows - 1;
if(tmpref.e.r > refguess.e.r) tmpref.e.r = refguess.e.r;
if(tmpref.e.r < tmpref.s.r) tmpref.s.r = tmpref.e.r;
@ -23556,7 +23564,14 @@ for(var cma = c; cma <= cc; ++cma) {
if(Rn[1]==='/'){
if((tmp=state.pop())[0]!==Rn[3]) throw new Error("Bad state: "+tmp.join("|"));
sheetnames.push(sheetname);
if(refguess.s.r <= refguess.e.r && refguess.s.c <= refguess.e.c) cursheet["!ref"] = encode_range(refguess);
if(refguess.s.r <= refguess.e.r && refguess.s.c <= refguess.e.c) {
cursheet["!ref"] = encode_range(refguess);
if(opts.sheetRows && opts.sheetRows <= refguess.e.r) {
cursheet["!fullref"] = cursheet["!ref"];
refguess.e.r = opts.sheetRows - 1;
cursheet["!ref"] = encode_range(refguess);
}
}
if(merges.length) cursheet["!merges"] = merges;
if(cstys.length > 0) cursheet["!cols"] = cstys;
if(rowinfo.length > 0) cursheet["!rows"] = rowinfo;
@ -24555,6 +24570,7 @@ function parse_workbook(blob, options) {
};
var addcell = function addcell(cell, line, options) {
if(file_depth > 1) return;
if(options.sheetRows && cell.r >= options.sheetRows) cell_valid = false;
if(!cell_valid) return;
if(options.cellStyles && line.XF && line.XF.data) process_cell_style(cell, line, options);
delete line.ixfe; delete line.XF;
@ -24578,8 +24594,7 @@ function parse_workbook(blob, options) {
break;
}
}
if(options.sheetRows && lastcell.r >= options.sheetRows) cell_valid = false;
else {
{
if(options.dense) {
if(!out[cell.r]) out[cell.r] = [];
out[cell.r][cell.c] = line;
@ -24744,6 +24759,13 @@ wb.opts.Date1904 = Workbook.WBProps.date1904 = val; break;
if(range.e.r > 0 && range.e.c > 0) {
range.e.r--; range.e.c--;
out["!ref"] = encode_range(range);
if(options.sheetRows && options.sheetRows <= range.e.r) {
var tmpri = range.e.r;
range.e.r = options.sheetRows - 1;
out["!fullref"] = out["!ref"];
out["!ref"] = encode_range(range);
range.e.r = tmpri;
}
range.e.r++; range.e.c++;
}
if(merges.length > 0) out["!merges"] = merges;
@ -26933,7 +26955,7 @@ var HTML_ = (function() {
for(i = 0; i < rows.length; ++i) {
var row = rows[i].trim();
var hd = row.slice(0,3).toLowerCase();
if(hd == "<tr") { ++R; C = 0; continue; }
if(hd == "<tr") { ++R; if(opts.sheetRows && opts.sheetRows <= R) { --R; break; } C = 0; continue; }
if(hd != "<td") continue;
var cells = row.split(/<\/td>/i);
for(j = 0; j < cells.length; ++j) {
@ -27037,10 +27059,11 @@ function parse_dom_table(table, _opts) {
if(DENSE != null) opts.dense = DENSE;
var ws = opts.dense ? ([]) : ({});
var rows = table.getElementsByTagName('tr');
var range = {s:{r:0,c:0},e:{r:rows.length - 1,c:0}};
var sheetRows = Math.min(opts.sheetRows||10000000, rows.length);
var range = {s:{r:0,c:0},e:{r:sheetRows - 1,c:0}};
var merges = [], midx = 0;
var R = 0, _C = 0, C = 0, RS = 0, CS = 0;
for(; R < rows.length; ++R) {
for(; R < sheetRows; ++R) {
var row = rows[R];
var elts = (row.children);
for(_C = C = 0; _C < elts.length; ++_C) {
@ -27074,6 +27097,7 @@ function parse_dom_table(table, _opts) {
}
ws['!merges'] = merges;
ws['!ref'] = encode_range(range);
if(sheetRows < rows.length) ws['!fullref'] = encode_range((range.e.r = rows.length-1,range));
return ws;
}
@ -27144,6 +27168,11 @@ var parse_content_xml = (function() {
case 'table': case '工作表': // 9.1.2 <table:table>
if(Rn[1]==='/') {
if(range.e.c >= range.s.c && range.e.r >= range.s.r) ws['!ref'] = encode_range(range);
if(opts.sheetRows > 0 && opts.sheetRows <= range.e.r) {
ws['!fullref'] = ws['!ref'];
range.e.r = opts.sheetRows - 1;
ws['!ref'] = encode_range(range);
}
if(merges.length) ws['!merges'] = merges;
if(rowinfo.length) ws["!rows"] = rowinfo;
sheetag.name = utf8read(sheetag['名称'] || sheetag.name);
@ -27260,7 +27289,7 @@ var parse_content_xml = (function() {
if(comments.length > 0) { q.c = comments; comments = []; }
if(textp && opts.cellText !== false) q.w = textp;
if(!isstub || opts.sheetStubs) {
if(!(opts.sheetRows && opts.sheetRows < R)) {
if(!(opts.sheetRows && opts.sheetRows <= R)) {
for(var rpt = 0; rpt < rowpeat; ++rpt) {
colpeat = parseInt(ctag['number-columns-repeated']||"1", 10);
if(opts.dense) {

20
dist/xlsx.full.min.js generated vendored

File diff suppressed because one or more lines are too long

2
dist/xlsx.full.min.map generated vendored

File diff suppressed because one or more lines are too long

63
dist/xlsx.js generated vendored

@ -4,7 +4,7 @@
/*global global, exports, module, require:false, process:false, Buffer:false, ArrayBuffer:false */
var XLSX = {};
(function make_xlsx(XLSX){
XLSX.version = '0.12.7';
XLSX.version = '0.12.8';
var current_codepage = 1200, current_ansi = 1252;
/*global cptable:true */
if(typeof module !== "undefined" && typeof require !== 'undefined') {
@ -5918,6 +5918,7 @@ var fields = [], field = ({});
}
}
if(ft != 0x02) if(d.l < d.length && d[d.l++] != 0x1A) throw new Error("DBF EOF Marker missing " + (d.l-1) + " of " + d.length + " " + d[d.l-1].toString(16));
if(opts && opts.sheetRows) out = out.slice(0, opts.sheetRows);
return out;
}
@ -5944,7 +5945,8 @@ function sheet_to_dbf(ws, opts) {
for(i = 0; i < headers.length; ++i) {
if(i == null) continue;
++hcnt;
if(typeof headers[i] !== 'string') throw new Error("DBF Invalid column name");
if(typeof headers[i] === 'number') headers[i] = headers[i].toString(10);
if(typeof headers[i] !== 'string') throw new Error("DBF Invalid column name " + headers[i] + " |" + (typeof headers[i]) + "|");
if(headers.indexOf(headers[i]) !== i) for(j=0; j<1024;++j)
if(headers.indexOf(headers[i] + "_" + j) == -1) { headers[i] += "_" + j; break; }
}
@ -6132,6 +6134,7 @@ var SYLK = (function() {
}
if(rowinfo.length > 0) sht['!rows'] = rowinfo;
if(colinfo.length > 0) sht['!cols'] = colinfo;
if(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);
return [arr, sht];
}
@ -6222,7 +6225,7 @@ var DIF = (function() {
}
throw new Error("Unrecognized type " + opts.type);
}
function dif_to_aoa_str(str) {
function dif_to_aoa_str(str, opts) {
var records = str.split('\n'), R = -1, C = -1, ri = 0, arr = [];
for (; ri !== records.length; ++ri) {
if (records[ri].trim() === 'BOT') { arr[++R] = []; C = 0; continue; }
@ -6250,6 +6253,7 @@ var DIF = (function() {
}
if (data === 'EOD') break;
}
if(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);
return arr;
}
@ -6323,7 +6327,7 @@ var ETH = (function() {
function decode(s) { return s.replace(/\\b/g,"\\").replace(/\\c/g,":").replace(/\\n/g,"\n"); }
function encode(s) { return s.replace(/\\/g, "\\b").replace(/:/g, "\\c").replace(/\n/g,"\\n"); }
function eth_to_aoa(str) {
function eth_to_aoa(str, opts) {
var records = str.split('\n'), R = -1, C = -1, ri = 0, arr = [];
for (; ri !== records.length; ++ri) {
var record = records[ri].trim().split(":");
@ -6344,6 +6348,7 @@ var ETH = (function() {
if(record[2] == 'vtf') arr[R][C] = [arr[R][C], _f];
}
}
if(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);
return arr;
}
@ -6451,6 +6456,7 @@ var PRN = (function() {
for(C = 1; C <= (lines[R].length - start)/10 + 1; ++C)
set_text_arr(lines[R].slice(start+(C-1)*10,start+C*10).trim(),arr,R,C,o);
}
if(o.sheetRows) arr = arr.slice(0, o.sheetRows);
return arr;
}
@ -6537,11 +6543,11 @@ var PRN = (function() {
start = end+1;
if(range.e.c < C) range.e.c = C;
if(range.e.r < R) range.e.r = R;
if(cc == sepcc) ++C; else { C = 0; ++R; }
if(cc == sepcc) ++C; else { C = 0; ++R; if(o.sheetRows && o.sheetRows <= R) return true; }
}
for(;end < str.length;++end) switch((cc=str.charCodeAt(end))) {
outer: for(;end < str.length;++end) switch((cc=str.charCodeAt(end))) {
case 0x22: instr = !instr; break;
case sepcc: case 0x0a: case 0x0d: if(!instr) finish_cell(); break;
case sepcc: case 0x0a: case 0x0d: if(!instr && finish_cell()) break outer; break;
default: break;
}
if(end - start > 0) finish_cell();
@ -6640,7 +6646,7 @@ var WK_ = (function() {
throw "Unsupported type " + opts.type;
}
function lotus_to_workbook_buf(d,opts) {
function lotus_to_workbook_buf(d, opts) {
if(!d) return d;
var o = opts || {};
if(DENSE != null && o.dense == null) o.dense = DENSE;
@ -6648,6 +6654,7 @@ var WK_ = (function() {
var sheets = {}, snames = [n];
var refguess = {s: {r:0, c:0}, e: {r:0, c:0} };
var sheetRows = o.sheetRows || 0;
if(d[2] == 0x02) o.Enum = WK1Enum;
else if(d[2] == 0x1a) o.Enum = WK3Enum;
@ -6695,6 +6702,7 @@ var WK_ = (function() {
sidx = val[3]; n = "Sheet" + (sidx + 1);
snames.push(n);
}
if(sheetRows > 0 && val[0].r >= sheetRows) break;
if(o.dense) {
if(!s[val[0].r]) s[val[0].r] = [];
s[val[0].r][val[0].c] = val[1];
@ -11896,7 +11904,7 @@ function parse_ws_xml(data, opts, idx, rels, wb, themes, styles) {
if(!s["!ref"] && refguess.e.c >= refguess.s.c && refguess.e.r >= refguess.s.r) s["!ref"] = encode_range(refguess);
if(opts.sheetRows > 0 && s["!ref"]) {
var tmpref = safe_decode_range(s["!ref"]);
if(opts.sheetRows < +tmpref.e.r) {
if(opts.sheetRows <= +tmpref.e.r) {
tmpref.e.r = opts.sheetRows - 1;
if(tmpref.e.r > refguess.e.r) tmpref.e.r = refguess.e.r;
if(tmpref.e.r < tmpref.s.r) tmpref.s.r = tmpref.e.r;
@ -13044,7 +13052,7 @@ function parse_ws_bin(data, _opts, idx, rels, wb, themes, styles) {
if(!s["!ref"] && (refguess.s.r < 2000000 || ref && (ref.e.r > 0 || ref.e.c > 0 || ref.s.r > 0 || ref.s.c > 0))) s["!ref"] = encode_range(ref || refguess);
if(opts.sheetRows && s["!ref"]) {
var tmpref = safe_decode_range(s["!ref"]);
if(opts.sheetRows < +tmpref.e.r) {
if(opts.sheetRows <= +tmpref.e.r) {
tmpref.e.r = opts.sheetRows - 1;
if(tmpref.e.r > refguess.e.r) tmpref.e.r = refguess.e.r;
if(tmpref.e.r < tmpref.s.r) tmpref.s.r = tmpref.e.r;
@ -14419,7 +14427,14 @@ for(var cma = c; cma <= cc; ++cma) {
if(Rn[1]==='/'){
if((tmp=state.pop())[0]!==Rn[3]) throw new Error("Bad state: "+tmp.join("|"));
sheetnames.push(sheetname);
if(refguess.s.r <= refguess.e.r && refguess.s.c <= refguess.e.c) cursheet["!ref"] = encode_range(refguess);
if(refguess.s.r <= refguess.e.r && refguess.s.c <= refguess.e.c) {
cursheet["!ref"] = encode_range(refguess);
if(opts.sheetRows && opts.sheetRows <= refguess.e.r) {
cursheet["!fullref"] = cursheet["!ref"];
refguess.e.r = opts.sheetRows - 1;
cursheet["!ref"] = encode_range(refguess);
}
}
if(merges.length) cursheet["!merges"] = merges;
if(cstys.length > 0) cursheet["!cols"] = cstys;
if(rowinfo.length > 0) cursheet["!rows"] = rowinfo;
@ -15418,6 +15433,7 @@ function parse_workbook(blob, options) {
};
var addcell = function addcell(cell, line, options) {
if(file_depth > 1) return;
if(options.sheetRows && cell.r >= options.sheetRows) cell_valid = false;
if(!cell_valid) return;
if(options.cellStyles && line.XF && line.XF.data) process_cell_style(cell, line, options);
delete line.ixfe; delete line.XF;
@ -15441,8 +15457,7 @@ function parse_w