@tensorflow/tfjs-core
Advanced tools
Comparing version 0.6.0 to 0.6.1
@@ -52,5 +52,7 @@ import { Conv2DInfo } from '../ops/conv_util'; | ||
maximum(a: Tensor, b: Tensor): Tensor; | ||
squaredDifference(a: Tensor, b: Tensor): Tensor; | ||
ceil<T extends Tensor>(x: T): T; | ||
floor<T extends Tensor>(x: T): T; | ||
exp<T extends Tensor>(x: T): T; | ||
expm1<T extends Tensor>(x: T): T; | ||
log<T extends Tensor>(x: T): T; | ||
@@ -77,2 +79,3 @@ log1p<T extends Tensor>(x: T): T; | ||
atan<T extends Tensor>(x: T): T; | ||
atan2<T extends Tensor>(a: T, b: T): T; | ||
sinh<T extends Tensor>(x: T): T; | ||
@@ -79,0 +82,0 @@ cosh<T extends Tensor>(x: T): T; |
@@ -516,2 +516,8 @@ "use strict"; | ||
}; | ||
MathBackendCPU.prototype.squaredDifference = function (a, b) { | ||
return this.broadcastedBinaryOp(a, b, a.dtype, function (aVal, bVal) { | ||
var diff = aVal - bVal; | ||
return diff * diff; | ||
}); | ||
}; | ||
MathBackendCPU.prototype.ceil = function (x) { | ||
@@ -541,2 +547,10 @@ var values = x.dataSync(); | ||
}; | ||
MathBackendCPU.prototype.expm1 = function (x) { | ||
var values = x.dataSync(); | ||
var newValues = new Float32Array(values.length); | ||
for (var i = 0; i < values.length; ++i) { | ||
newValues[i] = Math.expm1(values[i]); | ||
} | ||
return tensor_1.Tensor.make(x.shape, { values: newValues }); | ||
}; | ||
MathBackendCPU.prototype.log = function (x) { | ||
@@ -764,2 +778,5 @@ var values = x.dataSync(); | ||
}; | ||
MathBackendCPU.prototype.atan2 = function (a, b) { | ||
return this.broadcastedBinaryOp(a, b, a.dtype, function (aValue, bValue) { return Math.atan2(aValue, bValue); }); | ||
}; | ||
MathBackendCPU.prototype.sinh = function (x) { | ||
@@ -766,0 +783,0 @@ var resultValues = new Float32Array(x.size); |
@@ -81,2 +81,3 @@ import { TimingInfo } from '../engine'; | ||
maximum(a: Tensor, b: Tensor): Tensor; | ||
squaredDifference(a: Tensor, b: Tensor): Tensor; | ||
divide(a: Tensor, b: Tensor): Tensor; | ||
@@ -89,2 +90,3 @@ add(a: Tensor, b: Tensor): Tensor; | ||
exp<T extends Tensor>(x: T): T; | ||
expm1<T extends Tensor>(x: T): T; | ||
log<T extends Tensor>(x: T): T; | ||
@@ -111,2 +113,3 @@ log1p<T extends Tensor>(x: T): T; | ||
atan<T extends Tensor>(x: T): T; | ||
atan2<T extends Tensor>(a: T, b: T): T; | ||
sinh<T extends Tensor>(x: T): T; | ||
@@ -113,0 +116,0 @@ cosh<T extends Tensor>(x: T): T; |
@@ -502,2 +502,6 @@ "use strict"; | ||
}; | ||
MathBackendWebGL.prototype.squaredDifference = function (a, b) { | ||
var program = new binaryop_gpu_1.BinaryOpProgram(binaryop_gpu.SQUARED_DIFFERENCE, a.shape, b.shape); | ||
return this.compileAndRun(program, [a, b]); | ||
}; | ||
MathBackendWebGL.prototype.divide = function (a, b) { | ||
@@ -535,2 +539,6 @@ var program = new binaryop_gpu_1.BinaryOpProgram(binaryop_gpu.DIV, a.shape, b.shape); | ||
}; | ||
MathBackendWebGL.prototype.expm1 = function (x) { | ||
var program = new unaryop_gpu_1.UnaryOpProgram(x.shape, unary_op.EXPM1); | ||
return this.compileAndRun(program, [x]); | ||
}; | ||
MathBackendWebGL.prototype.log = function (x) { | ||
@@ -621,2 +629,6 @@ var program = new unaryop_gpu_1.UnaryOpProgram(x.shape, unary_op.LOG); | ||
}; | ||
MathBackendWebGL.prototype.atan2 = function (a, b) { | ||
var program = new binaryop_gpu_1.BinaryOpProgram(binaryop_gpu.ATAN2, a.shape, b.shape); | ||
return this.compileAndRun(program, [a, b]); | ||
}; | ||
MathBackendWebGL.prototype.sinh = function (x) { | ||
@@ -623,0 +635,0 @@ var program = new unaryop_gpu_1.UnaryOpProgram(x.shape, unary_op.SINH); |
@@ -51,2 +51,3 @@ import { Conv2DInfo } from '../ops/conv_util'; | ||
maximum(a: Tensor, b: Tensor): Tensor; | ||
squaredDifference(a: Tensor, b: Tensor): Tensor; | ||
ceil<T extends Tensor>(x: T): T; | ||
@@ -56,2 +57,3 @@ floor<T extends Tensor>(x: T): T; | ||
exp<T extends Tensor>(x: T): T; | ||
expm1<T extends Tensor>(x: T): T; | ||
log<T extends Tensor>(x: T): T; | ||
@@ -78,2 +80,3 @@ log1p<T extends Tensor>(x: T): T; | ||
atan<T extends Tensor>(x: T): T; | ||
atan2<T extends Tensor>(a: T, b: T): T; | ||
sinh<T extends Tensor>(x: T): T; | ||
@@ -80,0 +83,0 @@ cosh<T extends Tensor>(x: T): T; |
@@ -7,2 +7,3 @@ import { GPGPUProgram } from './gpgpu_math'; | ||
export declare const POW = "\n return (round(mod(b, 2.0)) == 0 || round(mod(b, 2.0)) == 2) ?\n pow(abs(a), b) : sign(a) * pow(abs(a), b);\n"; | ||
export declare const SQUARED_DIFFERENCE = "return (a - b) * (a - b);"; | ||
export declare const EQUAL: string; | ||
@@ -21,2 +22,3 @@ export declare const NOT_EQUAL: string; | ||
export declare const MIN: string; | ||
export declare const ATAN2: string; | ||
export declare class BinaryOpProgram implements GPGPUProgram { | ||
@@ -23,0 +25,0 @@ variableNames: string[]; |
@@ -10,2 +10,3 @@ "use strict"; | ||
exports.POW = "\n return (round(mod(b, 2.0)) == 0 || round(mod(b, 2.0)) == 2) ?\n pow(abs(a), b) : sign(a) * pow(abs(a), b);\n"; | ||
exports.SQUARED_DIFFERENCE = 'return (a - b) * (a - b);'; | ||
exports.EQUAL = CHECK_NAN_SNIPPET + "\n return float(a == b);\n"; | ||
@@ -24,2 +25,3 @@ exports.NOT_EQUAL = CHECK_NAN_SNIPPET + "\n return float(a != b);\n"; | ||
exports.MIN = CHECK_NAN_SNIPPET + "\n return min(a, b);\n"; | ||
exports.ATAN2 = CHECK_NAN_SNIPPET + "\n return atan(a, b);\n"; | ||
var BinaryOpProgram = (function () { | ||
@@ -26,0 +28,0 @@ function BinaryOpProgram(op, aShape, bShape) { |
@@ -79,5 +79,5 @@ "use strict"; | ||
var SAMPLE_4D_SNIPPET = "\nvec2 UVfrom4D(int texNumR, int texNumC, int stride0,\n int stride1, int stride2, int row, int col, int depth,\n int depth2) {\n // Explicitly use integer operations as dot() only works on floats.\n int index = row * stride0 + col * stride1 + depth * stride2 + depth2;\n int texR = index / texNumC;\n int texC = index - texR * texNumC;\n return (vec2(texC, texR) + halfCR) / vec2(texNumC, texNumR);\n}\n"; | ||
var UNSIGNED_BYTE_TEXTURE_SAMPLE_SNIPPET = "\n uniform float NaN;\n\n const vec4 floatDeltas = vec4(\n 1.0,\n 1.0 / 255.0,\n 1.0 / (255.0 * 255.0),\n 1.0 / (255.0 * 255.0 * 255.0)\n );\n const float minValue = " + tex_util.FLOAT_MIN + ".0;\n const float maxValue = " + tex_util.FLOAT_MAX + ".0;\n const float range = (maxValue - minValue) / 255.0;\n const vec2 dotRange = vec2(1.0, range);\n\n float sample(sampler2D texture, vec2 uv) {\n vec4 sampleValue = texture2D(texture, uv);\n if (all(equal(sampleValue, vec4(" + tex_util.BYTE_NAN_VALUE + ")))) {\n return NaN;\n }\n\n vec4 encValue = floor(sampleValue * 255.0 + 0.5);\n float decodedValue = dot(encValue, floatDeltas);\n return dot(vec2(minValue, decodedValue), dotRange);\n }\n"; | ||
var UNSIGNED_BYTE_TEXTURE_SAMPLE_SNIPPET = "\n uniform float NaN;\n\n const vec4 floatDeltas = vec4(\n 1.0,\n 1.0 / 255.0,\n 1.0 / (255.0 * 255.0),\n 1.0 / (255.0 * 255.0 * 255.0)\n );\n const float minValue = " + tex_util.FLOAT_MIN + ".0;\n const float maxValue = " + tex_util.FLOAT_MAX + ".0;\n const float range = (maxValue - minValue) / 255.0;\n const vec2 dotRange = vec2(1.0, range);\n\n float sampleTexture(sampler2D textureSampler, vec2 uv) {\n vec4 sampleValue = texture2D(textureSampler, uv);\n if (all(equal(sampleValue, vec4(" + tex_util.BYTE_NAN_VALUE + ")))) {\n return NaN;\n }\n\n vec4 encValue = floor(sampleValue * 255.0 + 0.5);\n float decodedValue = dot(encValue, floatDeltas);\n return dot(vec2(minValue, decodedValue), dotRange);\n }\n"; | ||
var UNSIGNED_BYTE_TEXTURE_SETOUTPUT_SNIPPET = "\n const vec4 floatPowers = vec4(\n 1.0,\n 255.0,\n 255.0 * 255.0,\n 255.0 * 255.0 * 255.0\n );\n const vec2 recipRange = vec2(1.0/range);\n const vec2 recipRange255 = vec2(1.0/(maxValue - minValue));\n\n void setOutput(float decodedValue) {\n if (isNaN(decodedValue)) {\n gl_FragColor = vec4(" + tex_util.BYTE_NAN_VALUE + ");\n return;\n }\n\n float a = dot(vec2(decodedValue, -minValue), recipRange);\n float b = fract(a) * 255.0;\n float c = fract(b) * 255.0;\n float d = fract(c) * 255.0;\n gl_FragColor = floor(vec4(a, b, c, d)) / 255.0;\n\n // TODO(dsmilkov): Version above gets better accuracy but probably slower\n // than the version below. Benchmark to determine if the accuracy is worth\n // the cost.\n\n // float normValue = dot(vec2(decodedValue, -minValue), recipRange255);\n // vec4 f = normValue * floatPowers;\n // gl_FragColor = floor(fract(f) * 255.0) / 255.0;\n }\n"; | ||
var FLOAT_TEXTURE_SAMPLE_SNIPPET = "\n float sample(sampler2D texture, vec2 uv) {\n return texture2D(texture, uv).r;\n }\n"; | ||
var FLOAT_TEXTURE_SAMPLE_SNIPPET = "\n float sampleTexture(sampler2D textureSampler, vec2 uv) {\n return texture2D(textureSampler, uv).r;\n }\n"; | ||
var FLOAT_TEXTURE_SETOUTPUT_SNIPPET = "\n void setOutput(float val) {\n gl_FragColor = vec4(val, 0, 0, 0);\n }\n"; | ||
@@ -123,3 +123,3 @@ var SHADER_PREFIX = "\n precision highp float;\n precision highp int;\n varying vec2 resultUV;\n const vec2 halfCR = vec2(0.5, 0.5);\n\n bool isNaN(float val) {\n float v1 = val * val;\n float v2 = val * val;\n return v1 == v2 ? false : true;\n }\n\n bool hasNaN(vec4 values) {\n vec4 v1 = values * values;\n vec4 v2 = values * values;\n return any(notEqual(v1, v2));\n }\n\n float getNaN(vec4 values) {\n return dot(vec4(1), values);\n }\n\n int round(float value) {\n return int(floor(value + 0.5));\n }\n\n int imod(int x, int y) {\n return x - y * (x / y);\n }\n\n const vec2 randomConst = vec2(\n 23.14069263277926, // e^pi (Gelfond's constant)\n 2.665144142690225 // 2^sqrt(2) (Gelfond\u2013Schneider constant)\n );\n\n float random(float seed) {\n return fract(cos(dot(resultUV * seed, randomConst)) * 12345.6789);\n }\n\n " + SAMPLE_1D_SNIPPET + "\n " + SAMPLE_2D_SNIPPET + "\n " + SAMPLE_3D_SNIPPET + "\n " + SAMPLE_4D_SNIPPET + "\n"; | ||
var funcName = 'get' + texName.charAt(0).toUpperCase() + texName.slice(1); | ||
return "\n float " + funcName + "() {\n return sample(" + texName + ", halfCR);\n }\n "; | ||
return "\n float " + funcName + "() {\n return sampleTexture(" + texName + ", halfCR);\n }\n "; | ||
} | ||
@@ -139,3 +139,3 @@ function getSampler1D(inputInfo) { | ||
if (util.arraysEqual(shape, texShape)) { | ||
return "\n float " + funcName + "(int row, int col) {\n vec2 uv = (vec2(col, row) + halfCR) / vec2(" + texNumC + ".0, " + texNumR + ".0);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int row, int col) {\n vec2 uv = (vec2(col, row) + halfCR) / vec2(" + texNumC + ".0, " + texNumR + ".0);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
@@ -150,8 +150,8 @@ var _a = util.squeezeShape(shape), newShape = _a.newShape, keptDims = _a.keptDims; | ||
if (texNumC === 1) { | ||
return "\n float " + funcName + "(int row, int col) {\n int index = row * " + shape[1] + " + col;\n vec2 uv = vec2(0.5, (float(index) + 0.5) / " + texNumR + ".0);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int row, int col) {\n int index = row * " + shape[1] + " + col;\n vec2 uv = vec2(0.5, (float(index) + 0.5) / " + texNumR + ".0);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
if (texNumR === 1) { | ||
return "\n float " + funcName + "(int row, int col) {\n int index = row * " + shape[1] + " + col;\n vec2 uv = vec2((float(index) + 0.5) / " + texNumC + ".0, 0.5);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int row, int col) {\n int index = row * " + shape[1] + " + col;\n vec2 uv = vec2((float(index) + 0.5) / " + texNumC + ".0, 0.5);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
return "\n float " + funcName + "(int row, int col) {\n vec2 uv = UVfrom2D(" + texNumR + ", " + texNumC + ", " + shape[1] + ", row, col);\n return sample(" + texName + ", uv);\n }\n"; | ||
return "\n float " + funcName + "(int row, int col) {\n vec2 uv = UVfrom2D(" + texNumR + ", " + texNumC + ", " + shape[1] + ", row, col);\n return sampleTexture(" + texName + ", uv);\n }\n"; | ||
} | ||
@@ -175,8 +175,8 @@ function getSampler3D(inputInfo) { | ||
if (texNumC === stride0) { | ||
return "\n float " + funcName + "(int row, int col, int depth) {\n int texR = row;\n int texC = col * " + stride1 + " + depth;\n vec2 uv = (vec2(texC, texR) + halfCR) /\n vec2(" + texNumC + ".0, " + texNumR + ".0);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int row, int col, int depth) {\n int texR = row;\n int texC = col * " + stride1 + " + depth;\n vec2 uv = (vec2(texC, texR) + halfCR) /\n vec2(" + texNumC + ".0, " + texNumR + ".0);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
if (texNumC === stride1) { | ||
return "\n float " + funcName + "(int row, int col, int depth) {\n int texR = row * " + shape[1] + " + col;\n int texC = depth;\n vec2 uv = (vec2(texC, texR) + halfCR) / vec2(" + texNumC + ".0, " + texNumR + ".0);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int row, int col, int depth) {\n int texR = row * " + shape[1] + " + col;\n int texC = depth;\n vec2 uv = (vec2(texC, texR) + halfCR) / vec2(" + texNumC + ".0, " + texNumR + ".0);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
return "\n float " + funcName + "(int row, int col, int depth) {\n vec2 uv = UVfrom3D(\n " + texNumR + ", " + texNumC + ", " + stride0 + ", " + stride1 + ", row, col, depth);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int row, int col, int depth) {\n vec2 uv = UVfrom3D(\n " + texNumR + ", " + texNumC + ", " + stride0 + ", " + stride1 + ", row, col, depth);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
@@ -200,8 +200,8 @@ function getSampler4D(inputInfo) { | ||
if (texNumC === stride0) { | ||
return "\n float " + funcName + "(int row, int col, int depth, int depth2) {\n int texR = row;\n int texC = col * " + stride1 + " + depth * " + stride2 + " + depth2;\n vec2 uv = (vec2(texC, texR) + halfCR) /\n vec2(" + texNumC + ".0, " + texNumR + ".0);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int row, int col, int depth, int depth2) {\n int texR = row;\n int texC = col * " + stride1 + " + depth * " + stride2 + " + depth2;\n vec2 uv = (vec2(texC, texR) + halfCR) /\n vec2(" + texNumC + ".0, " + texNumR + ".0);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
if (texNumC === stride2) { | ||
return "\n float " + funcName + "(int row, int col, int depth, int depth2) {\n int texR = row * " + shape[1] * shape[2] + " + col * " + shape[2] + " + depth;\n int texC = depth2;\n vec2 uv = (vec2(texC, texR) + halfCR) /\n vec2(" + texNumC + ".0, " + texNumR + ".0);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int row, int col, int depth, int depth2) {\n int texR = row * " + shape[1] * shape[2] + " + col * " + shape[2] + " + depth;\n int texC = depth2;\n vec2 uv = (vec2(texC, texR) + halfCR) /\n vec2(" + texNumC + ".0, " + texNumR + ".0);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
return "\n float " + funcName + "(int row, int col, int depth, int depth2) {\n vec2 uv = UVfrom4D(" + texNumR + ", " + texNumC + ", " + stride0 + ", " + stride1 + ",\n " + stride2 + ", row, col, depth, depth2);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int row, int col, int depth, int depth2) {\n vec2 uv = UVfrom4D(" + texNumR + ", " + texNumC + ", " + stride0 + ", " + stride1 + ",\n " + stride2 + ", row, col, depth, depth2);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
@@ -215,11 +215,11 @@ function getSamplerFlat(inputInfo) { | ||
if (tNumC === 1 && tNumR === 1) { | ||
return "\n float " + funcName + "(int index) {\n return sample(" + texName + ", halfCR);\n }\n "; | ||
return "\n float " + funcName + "(int index) {\n return sampleTexture(" + texName + ", halfCR);\n }\n "; | ||
} | ||
if (tNumC === 1) { | ||
return "\n float " + funcName + "(int index) {\n vec2 uv = vec2(0.5, (float(index) + 0.5) / " + tNumR + ".0);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int index) {\n vec2 uv = vec2(0.5, (float(index) + 0.5) / " + tNumR + ".0);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
if (tNumR === 1) { | ||
return "\n float " + funcName + "(int index) {\n vec2 uv = vec2((float(index) + 0.5) / " + tNumC + ".0, 0.5);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int index) {\n vec2 uv = vec2((float(index) + 0.5) / " + tNumC + ".0, 0.5);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
return "\n float " + funcName + "(int index) {\n vec2 uv = UVfrom1D(" + tNumR + ", " + tNumC + ", index);\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "(int index) {\n vec2 uv = UVfrom1D(" + tNumR + ", " + tNumC + ", index);\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
@@ -278,3 +278,3 @@ function getBroadcastOutputCoordsSampler(inputInfo, outShapeInfo, texFuncSnippet, funcName) { | ||
if (util.arraysEqual(inTexShape, outTexShape)) { | ||
return "\n float " + funcName + "() {\n return sample(" + texName + ", resultUV);\n }\n "; | ||
return "\n float " + funcName + "() {\n return sampleTexture(" + texName + ", resultUV);\n }\n "; | ||
} | ||
@@ -286,3 +286,3 @@ var inSize = util.sizeFromShape(inTexShape); | ||
} | ||
return "\n float " + funcName + "() {\n ivec2 resTexRC = ivec2(resultUV.yx *\n vec2(" + outTexShape[0] + ", " + outTexShape[1] + "));\n int index = resTexRC.x * " + outTexShape[1] + " + resTexRC.y;\n " + broadcastSnippet + "\n int texR = index / " + inTexShape[1] + ";\n int texC = index - texR * " + inTexShape[1] + ";\n vec2 uv = (vec2(texC, texR) + halfCR) /\n vec2(" + inTexShape[1] + ".0, " + inTexShape[0] + ".0);\n\n return sample(" + texName + ", uv);\n }\n "; | ||
return "\n float " + funcName + "() {\n ivec2 resTexRC = ivec2(resultUV.yx *\n vec2(" + outTexShape[0] + ", " + outTexShape[1] + "));\n int index = resTexRC.x * " + outTexShape[1] + " + resTexRC.y;\n " + broadcastSnippet + "\n int texR = index / " + inTexShape[1] + ";\n int texC = index - texR * " + inTexShape[1] + ";\n vec2 uv = (vec2(texC, texR) + halfCR) /\n vec2(" + inTexShape[1] + ".0, " + inTexShape[0] + ".0);\n\n return sampleTexture(" + texName + ", uv);\n }\n "; | ||
} | ||
@@ -289,0 +289,0 @@ function getCoordsDataType(rank) { |
@@ -19,2 +19,3 @@ import { GPGPUProgram } from './gpgpu_math'; | ||
export declare const EXP = "\n return exp(x);\n"; | ||
export declare const EXPM1 = "\n return exp(x) - 1.0;\n"; | ||
export declare const LOG = "\n return log(x);\n"; | ||
@@ -21,0 +22,0 @@ export declare const LOG1P = "\n return log(1.0 + x);\n"; |
@@ -32,2 +32,3 @@ "use strict"; | ||
exports.EXP = "\n return exp(x);\n"; | ||
exports.EXPM1 = "\n return exp(x) - 1.0;\n"; | ||
exports.LOG = "\n return log(x);\n"; | ||
@@ -34,0 +35,0 @@ exports.LOG1P = "\n return log(1.0 + x);\n"; |
@@ -17,2 +17,5 @@ import { Tensor } from '../tensor'; | ||
static maximumStrict<T extends Tensor>(a: T, b: T): T; | ||
static squaredDifference<T extends Tensor>(a: Tensor, b: Tensor): T; | ||
static squaredDifferenceStrict<T extends Tensor>(a: T, b: T): T; | ||
static atan2<T extends Tensor>(a: Tensor, b: Tensor): T; | ||
} |
@@ -123,2 +123,3 @@ "use strict"; | ||
BinaryOps.div = function (a, b) { | ||
util.assertTypesMatch(a, b); | ||
var outShape = broadcast_util.assertAndGetBroadcastShape(a.shape, b.shape); | ||
@@ -179,2 +180,43 @@ var der = function (dy) { | ||
}; | ||
BinaryOps.squaredDifference = function (a, b) { | ||
util.assertTypesMatch(a, b); | ||
broadcast_util.assertAndGetBroadcastShape(a.shape, b.shape); | ||
var der = function (dy) { | ||
var two = ops_1.scalar(2); | ||
var derA = function () { return dy.mul(a.sub(b).mul(two)); }; | ||
var derB = function () { return dy.mul(b.sub(a).mul(two)); }; | ||
return { a: derA, b: derB }; | ||
}; | ||
return environment_1.ENV.engine.runKernel(function (backend) { return backend.squaredDifference(a, b); }, { a: a, b: b }, der); | ||
}; | ||
BinaryOps.squaredDifferenceStrict = function (a, b) { | ||
util.assertShapesMatch(a.shape, b.shape, 'Error in squaredDifferenceStrict: '); | ||
return a.squaredDifference(b); | ||
}; | ||
BinaryOps.atan2 = function (a, b) { | ||
util.assertTypesMatch(a, b); | ||
var outShape = broadcast_util.assertAndGetBroadcastShape(a.shape, b.shape); | ||
var der = function (dy) { | ||
var derA = function () { | ||
var d = BinaryOps.add(ops_1.square(a), ops_1.square(b)); | ||
var res = dy.mul(b.div(d)); | ||
var reduceAxes = broadcast_util.getReductionAxes(a.shape, outShape); | ||
if (reduceAxes.length > 0) { | ||
res = res.sum(reduceAxes); | ||
} | ||
return res.reshape(a.shape); | ||
}; | ||
var derB = function () { | ||
var d = BinaryOps.add(ops_1.square(a), ops_1.square(b)); | ||
var res = ops_1.neg(dy.mul(a.div(d))); | ||
var reduceAxes = broadcast_util.getReductionAxes(b.shape, outShape); | ||
if (reduceAxes.length > 0) { | ||
res = res.sum(reduceAxes); | ||
} | ||
return res.reshape(b.shape); | ||
}; | ||
return { a: derA, b: derB }; | ||
}; | ||
return environment_1.ENV.engine.runKernel(function (backend) { return backend.atan2(a, b); }, { a: a, b: b }, der); | ||
}; | ||
__decorate([ | ||
@@ -229,4 +271,14 @@ doc_1.doc({ heading: 'Operations', subheading: 'Arithmetic' }), | ||
], BinaryOps, "maximumStrict", null); | ||
__decorate([ | ||
doc_1.doc({ heading: 'Operations', subheading: 'Arithmetic' }), | ||
operation_1.operation | ||
], BinaryOps, "squaredDifference", null); | ||
__decorate([ | ||
operation_1.operation | ||
], BinaryOps, "squaredDifferenceStrict", null); | ||
__decorate([ | ||
operation_1.operation | ||
], BinaryOps, "atan2", null); | ||
return BinaryOps; | ||
}()); | ||
exports.BinaryOps = BinaryOps; |
@@ -86,2 +86,3 @@ import { ArrayOps } from './array_ops'; | ||
export declare const exp: typeof UnaryOps.exp; | ||
export declare const expm1: typeof UnaryOps.expm1; | ||
export declare const floor: typeof UnaryOps.floor; | ||
@@ -104,2 +105,3 @@ export declare const leakyRelu: typeof UnaryOps.leakyRelu; | ||
export declare const add: typeof BinaryOps.add; | ||
export declare const atan2: typeof BinaryOps.atan2; | ||
export declare const addStrict: typeof BinaryOps.addStrict; | ||
@@ -118,2 +120,4 @@ export declare const div: typeof BinaryOps.div; | ||
export declare const subStrict: typeof BinaryOps.subStrict; | ||
export declare const squaredDifference: typeof BinaryOps.squaredDifference; | ||
export declare const squaredDifferenceStrict: typeof BinaryOps.squaredDifferenceStrict; | ||
export declare const norm: typeof NormOps.norm; | ||
@@ -120,0 +124,0 @@ export declare const cast: typeof ArrayOps.cast; |
@@ -88,2 +88,3 @@ "use strict"; | ||
exports.exp = unary_ops_1.UnaryOps.exp; | ||
exports.expm1 = unary_ops_1.UnaryOps.expm1; | ||
exports.floor = unary_ops_1.UnaryOps.floor; | ||
@@ -106,2 +107,3 @@ exports.leakyRelu = unary_ops_1.UnaryOps.leakyRelu; | ||
exports.add = binary_ops_1.BinaryOps.add; | ||
exports.atan2 = binary_ops_1.BinaryOps.atan2; | ||
exports.addStrict = binary_ops_1.BinaryOps.addStrict; | ||
@@ -120,2 +122,4 @@ exports.div = binary_ops_1.BinaryOps.div; | ||
exports.subStrict = binary_ops_1.BinaryOps.subStrict; | ||
exports.squaredDifference = binary_ops_1.BinaryOps.squaredDifference; | ||
exports.squaredDifferenceStrict = binary_ops_1.BinaryOps.squaredDifferenceStrict; | ||
exports.norm = norm_1.NormOps.norm; | ||
@@ -122,0 +126,0 @@ exports.cast = array_ops_1.ArrayOps.cast; |
@@ -75,3 +75,6 @@ "use strict"; | ||
var reduceSizeScalar = ops.scalar(reduceSize); | ||
var res = x.div(reduceSizeScalar); | ||
var xReduce = reduceSizeScalar.dtype === x.dtype ? | ||
x : | ||
x.cast(reduceSizeScalar.dtype); | ||
var res = xReduce.div(reduceSizeScalar); | ||
var value = res.sum(axis, keepDims); | ||
@@ -78,0 +81,0 @@ var gradFunc = function (dy) { |
@@ -7,2 +7,3 @@ import { Tensor } from '../tensor'; | ||
static exp<T extends Tensor>(x: T): T; | ||
static expm1<T extends Tensor>(x: T): T; | ||
static log<T extends Tensor>(x: T): T; | ||
@@ -9,0 +10,0 @@ static log1p<T extends Tensor>(x: T): T; |
@@ -44,2 +44,8 @@ "use strict"; | ||
}; | ||
UnaryOps.expm1 = function (x) { | ||
var grad = function (dy) { | ||
return { x: function () { return dy.mulStrict(x.exp()); } }; | ||
}; | ||
return environment_1.ENV.engine.runKernel(function (backend) { return backend.expm1(x); }, { x: x }, grad); | ||
}; | ||
UnaryOps.log = function (x) { | ||
@@ -224,2 +230,6 @@ var grad = function (dy) { | ||
operation_1.operation | ||
], UnaryOps, "expm1", null); | ||
__decorate([ | ||
doc_1.doc({ heading: 'Operations', subheading: 'Basic math' }), | ||
operation_1.operation | ||
], UnaryOps, "log", null); | ||
@@ -226,0 +236,0 @@ __decorate([ |
@@ -74,2 +74,3 @@ import { DataType, Rank, ShapeMap, TypedArray } from './types'; | ||
argMax<T extends Tensor>(axis?: number): T; | ||
cast<T extends this>(dtype: DataType): T; | ||
add<T extends Tensor>(x: Tensor): T; | ||
@@ -89,2 +90,4 @@ addStrict<T extends this>(this: T, x: T): T; | ||
maximumStrict<T extends this>(this: T, x: T): T; | ||
squaredDifference<T extends Tensor>(x: Tensor): T; | ||
squaredDifferenceStrict<T extends this>(this: T, x: T): T; | ||
transpose<T extends Tensor>(this: T, perm?: number[]): T; | ||
@@ -111,2 +114,3 @@ notEqual<T extends Tensor>(x: Tensor): T; | ||
exp<T extends Tensor>(this: T): T; | ||
expm1<T extends Tensor>(this: T): T; | ||
log<T extends Tensor>(this: T): T; | ||
@@ -113,0 +117,0 @@ log1p<T extends Tensor>(this: T): T; |
@@ -380,2 +380,6 @@ "use strict"; | ||
}; | ||
Tensor.prototype.cast = function (dtype) { | ||
this.throwIfDisposed(); | ||
return ops.cast(this, dtype); | ||
}; | ||
Tensor.prototype.add = function (x) { | ||
@@ -437,2 +441,10 @@ this.throwIfDisposed(); | ||
}; | ||
Tensor.prototype.squaredDifference = function (x) { | ||
this.throwIfDisposed(); | ||
return ops.squaredDifference(this, x); | ||
}; | ||
Tensor.prototype.squaredDifferenceStrict = function (x) { | ||
this.throwIfDisposed(); | ||
return ops.squaredDifferenceStrict(this, x); | ||
}; | ||
Tensor.prototype.transpose = function (perm) { | ||
@@ -522,2 +534,6 @@ this.throwIfDisposed(); | ||
}; | ||
Tensor.prototype.expm1 = function () { | ||
this.throwIfDisposed(); | ||
return ops.expm1(this); | ||
}; | ||
Tensor.prototype.log = function () { | ||
@@ -524,0 +540,0 @@ this.throwIfDisposed(); |
@@ -110,6 +110,8 @@ "use strict"; | ||
describe(testName, function () { | ||
beforeEach(function () { | ||
beforeAll(function () { | ||
environment_1.ENV.setFeatures(features || {}); | ||
environment_1.ENV.addCustomBackend('webgl', function () { return new backend_webgl_1.MathBackendWebGL(); }); | ||
environment_1.ENV.addCustomBackend('cpu', function () { return new backend_cpu_1.MathBackendCPU(); }); | ||
}); | ||
beforeEach(function () { | ||
if (features && features.BACKEND != null) { | ||
@@ -122,2 +124,4 @@ environment_1.Environment.setBackend(features.BACKEND); | ||
environment_1.ENV.engine.endScope(null); | ||
}); | ||
afterAll(function () { | ||
environment_1.ENV.reset(); | ||
@@ -124,0 +128,0 @@ }); |
@@ -1,2 +0,2 @@ | ||
declare const version = "0.6.0"; | ||
declare const version = "0.6.1"; | ||
export { version }; |
"use strict"; | ||
Object.defineProperty(exports, "__esModule", { value: true }); | ||
var version = '0.6.0'; | ||
var version = '0.6.1'; | ||
exports.version = version; |
@@ -12,2 +12,2 @@ import { NamedTensorMap } from './types'; | ||
} | ||
export declare function loadWeights(manifest: WeightsManifestConfig, filePathPrefix?: string, weightNames?: string[]): Promise<NamedTensorMap>; | ||
export declare function loadWeights(manifest: WeightsManifestConfig, filePathPrefix?: string, weightNames?: string[], requestOptions?: RequestInit): Promise<NamedTensorMap>; |
@@ -44,3 +44,3 @@ "use strict"; | ||
}; | ||
function loadWeights(manifest, filePathPrefix, weightNames) { | ||
function loadWeights(manifest, filePathPrefix, weightNames, requestOptions) { | ||
if (filePathPrefix === void 0) { filePathPrefix = ''; } | ||
@@ -105,3 +105,3 @@ return __awaiter(this, void 0, void 0, function () { | ||
(!filePathPrefix.endsWith('/') ? '/' : '') + filepath; | ||
requests.push(fetch(fetchUrl)); | ||
requests.push(fetch(fetchUrl, requestOptions)); | ||
}); | ||
@@ -108,0 +108,0 @@ }); |
{ | ||
"name": "@tensorflow/tfjs-core", | ||
"version": "0.6.0", | ||
"version": "0.6.1", | ||
"description": "Hardware-accelerated JavaScript library for machine intelligence", | ||
@@ -12,3 +12,3 @@ "private": false, | ||
"type": "git", | ||
"url": "https://github.com/PAIR-code/deeplearnjs.git" | ||
"url": "https://github.com/tensorflow/tfjs-core.git" | ||
}, | ||
@@ -15,0 +15,0 @@ "license": "Apache-2.0", |
185
README.md
@@ -1,173 +0,50 @@ | ||
<a id="travis-badge" href="https://travis-ci.org/PAIR-code/deeplearnjs" alt="Build Status"> | ||
<img src="https://travis-ci.org/PAIR-code/deeplearnjs.svg?branch=master" /> | ||
<a id="travis-badge" href="https://travis-ci.org/tensorflow/tfjs-core" alt="Build Status"> | ||
<img src="https://travis-ci.org/tensorflow/tfjs-core.svg?branch=master" /> | ||
</a> | ||
# Getting started | ||
# TensorFlow.js Core API | ||
**deeplearn.js** is an open source hardware-accelerated JavaScript library for | ||
machine intelligence. **deeplearn.js** brings performant machine learning | ||
building blocks to the web, allowing you to train neural networks in a browser | ||
or run pre-trained models in inference mode. | ||
> NOTE: Building on the momentum of deeplearn.js, we have joined the TensorFlow | ||
family and we are starting a new ecosystem of libraries and tools for Machine | ||
Learning in Javascript, called [TensorFlow.js](https://js.tensorflow.org). | ||
This repo moved from `PAIR-code/deeplearnjs` to `tensorflow/tfjs-core`. | ||
We provide an API that closely mirrors the TensorFlow eager API. | ||
**deeplearn.js** was originally developed by the Google Brain PAIR team to build | ||
powerful interactive machine learning tools for the browser, but it can be used | ||
for everything from education, to model understanding, to art projects. | ||
A part of the TensorFlow.js ecosystem, this repo hosts `@tensorflow/tfjs-core`, | ||
the TensorFlow.js Core API, which provides low-level, hardware-accelerated | ||
linear algebra operations and an eager API for automatic differentiation. | ||
## Usage | ||
Check out [js.tensorflow.org](https://js.tensorflow.org) for more | ||
information about the library, tutorials and API docs. | ||
You can install this library via yarn/npm: `yarn add deeplearn` | ||
or `npm install deeplearn` | ||
To keep track of issues, we use the [tensorflow/tfjs](https://github.com/tensorflow/tfjs) Github repo. | ||
Alternatively you can use a script tag. Here we load it from a CDN. | ||
In this case it will be available as a global variable named `dl`. | ||
## Importing | ||
You can replace also specify which version to load replacing `@latest` with a specific | ||
version string (e.g. `0.5.0`). | ||
You can install TensorFlow.js via yarn or npm. We recommend using the | ||
[@tensorflow/tfjs](https://www.npmjs.com/package/@tensorflow/tfjs) npm package, | ||
which gives you both this Core API and the higher-level | ||
[Layers API](https://github.com/tensorflow/tfjs-layers): | ||
```html | ||
<script src="https://cdn.jsdelivr.net/npm/deeplearn@latest"></script> | ||
<!-- or --> | ||
<script src="https://unpkg.com/deeplearn@latest"></script> | ||
``` | ||
#### TypeScript / ES6 JavaScript | ||
Let's add a scalar value to a 1D Tensor. Deeplearn js supports _broadcasting_ | ||
the value of scalar over all the elements in the tensor. | ||
```js | ||
import * as dl from 'deeplearn'; // If not loading the script as a global | ||
const a = dl.tensor1d([1, 2, 3]); | ||
const b = dl.scalar(2); | ||
const result = a.add(b); // a is not modified, result is a new tensor | ||
result.data().then(data => console.log(data)); // Float32Array([3, 4, 5] | ||
// Alternatively you can use a blocking call to get the data. | ||
// However this might slow your program down if called repeatedly. | ||
console.log(result.dataSync()); // Float32Array([3, 4, 5] | ||
import * as tf from '@tensorflow/tfjs'; | ||
// You have the Core API: tf.matMul(), tf.softmax(), ... | ||
// You also have Layers API: tf.model(), tf.layers.dense(), ... | ||
``` | ||
See the [TypeScript starter project](https://github.com/PAIR-code/deeplearnjs/tree/master/starter/typescript/) and the | ||
[ES6 starter project](https://github.com/PAIR-code/deeplearnjs/tree/master/starter/es6/) to get you quickly started. | ||
On the other hand, if you care about the bundle size and you do not use the | ||
Layers API, you can import only the Core API: | ||
#### ES5 JavaScript | ||
Let's do the same thing in ES5 Javascript. Remember to include the script tag to | ||
load deeplearn.js | ||
```js | ||
var a = dl.tensor1d([1, 2, 3]); | ||
var b = dl.scalar(2); | ||
var result = a.add(b); // a is not modified, result is a new tensor | ||
// Option 1: With a Promise. | ||
result.data().then(data => console.log(data)); // Float32Array([3, 4, 5]) | ||
// Option 2: Synchronous download of data. Blocks the UI. | ||
console.log(result.dataSync()); | ||
import * as tfc from '@tensorflow/tfjs-core'; | ||
// You have the Core API: tfc.matMul(), tfc.softmax(), ... | ||
// No Layers API. | ||
``` | ||
## Development | ||
For info about development, check out [DEVELOPMENT.md](./DEVELOPMENT.md). | ||
To build **deeplearn.js** from source, we need to clone the project and prepare | ||
the dev environment: | ||
## For more information | ||
```bash | ||
$ git clone https://github.com/PAIR-code/deeplearnjs.git | ||
$ cd deeplearnjs | ||
$ yarn # Installs dependencies. | ||
``` | ||
- [TensorFlow.js API documentation](https://js.tensorflow.org/api/latest/) | ||
- [TensorFlow.js Tutorials](https://js.tensorflow.org/tutorials/) | ||
#### Yarn vs NPM | ||
Generally speaking it's up to you. Yarn is fully interoperable with npm. You can either do `yarn` or `npm install`. However we use yarn, and if you are adding or removing dependencies you should use yarn to keep the `yarn.lock` file up to date. | ||
#### Code editor | ||
We recommend using [Visual Studio Code](https://code.visualstudio.com/) for | ||
development. Make sure to install | ||
[TSLint VSCode extension](https://marketplace.visualstudio.com/items?itemName=eg2.tslint) | ||
and the npm [clang-format](https://github.com/angular/clang-format) `1.2.2` or later | ||
with the | ||
[Clang-Format VSCode extension](https://marketplace.visualstudio.com/items?itemName=xaver.clang-format) | ||
for auto-formatting. | ||
#### Interactive development | ||
To interactively develop any of the demos (e.g. `demos/nn-art/`): | ||
```bash | ||
$ ./scripts/watch-demo demos/nn-art | ||
>> Starting up http-server, serving ./ | ||
>> Available on: | ||
>> http://127.0.0.1:8080 | ||
>> Hit CTRL-C to stop the server | ||
>> 1357589 bytes written to dist/demos/nn-art/bundle.js (0.85 seconds) at 10:34:45 AM | ||
``` | ||
Then visit `http://localhost:8080/demos/nn-art/`. The | ||
`watch-demo` script monitors for changes of typescript code and does | ||
incremental compilation (~200-400ms), so users can have a fast edit-refresh | ||
cycle when developing apps. | ||
#### Testing | ||
Before submitting a pull request, make sure the code passes all the tests and is clean of lint errors: | ||
```bash | ||
$ yarn test | ||
$ yarn lint | ||
``` | ||
To run a subset of tests and/or on a specific browser: | ||
```bash | ||
$ yarn test --browsers=Chrome --grep='multinomial' | ||
> ... | ||
> Chrome 62.0.3202 (Mac OS X 10.12.6): Executed 28 of 1891 (skipped 1863) SUCCESS (6.914 secs / 0.634 secs) | ||
``` | ||
To run the tests once and exit the karma process (helpful on Windows): | ||
```bash | ||
$ yarn test --single-run | ||
``` | ||
#### Packaging (browser and npm) | ||
```bash | ||
$ yarn build-npm | ||
> Stored standalone library at dist/deeplearn(.min).js | ||
> deeplearn-VERSION.tgz | ||
``` | ||
To install it locally, run `npm install ./deeplearn-VERSION.tgz`. | ||
> On Windows, use bash (available through git) to use the scripts above. | ||
Looking to contribute, and don't know where to start? Check out our "help wanted" | ||
[issues](https://github.com/PAIR-code/deeplearnjs/issues?q=is%3Aissue+is%3Aopen+label%3A%22help+wanted%22). | ||
## Supported environments | ||
**deeplearn.js** targets environments with WebGL 1.0 or WebGL 2.0. For devices | ||
without the `OES_texture_float` extension, we fall back to fixed precision | ||
floats backed by a `gl.UNSIGNED_BYTE` texture. For platforms without WebGL, | ||
we provide CPU fallbacks. | ||
## Resources | ||
* [Tutorials](https://deeplearnjs.org/docs/tutorials/index.html) | ||
* [API Reference](https://deeplearnjs.org/docs/api/index.html) | ||
* [Demos](https://deeplearnjs.org/index.html#demos) | ||
* [Roadmap](https://deeplearnjs.org/docs/roadmap.html) | ||
## Thanks | ||
<p style="display:flex; align-items:center;"> | ||
<a href="https://www.browserstack.com/"> | ||
<img src="https://www.browserstack.com/images/layout/browserstack-logo-600x315.png" height="70" style="height:70px;"> | ||
</a> | ||
<span> for providing testing support.</span> | ||
</p> | ||
Thanks <a href="https://www.browserstack.com/">BrowserStack</a> for providing testing support. |
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is too big to display
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
2225391
318
40874
51