I am trying to track down how to get to delta1 and delta2 in the R simpleLoess function that is called by the loess function.
In the simpleLoess function there is a call
z <- .C(C_loess_raw, y, x, if (no.st) 1 else weights,
if (no.st) weights * robust else 1, D, N, as.double(span),
as.integer(degree), as.integer(nonparametric), as.integer(order.drop.sqr),
as.integer(sum.drop.sqr), as.double(span * cell),
as.character(surf.stat), fitted.values = double(N),
parameter = integer(7L), a = integer(max.kd), xi = double(max.kd),
vert = double(2L * D), vval = double((D + 1L) * max.kd),
diagonal = double(N), trL = double(1L), delta1 = double(1L),
delta2 = double(1L), as.integer(surf.stat == "interpolate/exact"))
Which calls some C code which itself calls some fortran code. Then the delta1 and delta2 are just extracted as:
one.delta <- z$delta1
two.delta <- z$delta2
That is called in the c function here. That itself calls some fortran here. At this point I'm at a loss -- any suggestions on how the actual delta1 and delta2 are calculated so that I can recreate it would be very helpful...
Related
I'm making a mode 7/perspective projection project in Godot. When I run it, it produces the expected effect, displaying a 2d image as if it were a 3d plane.
Code:
func _ready():
map.load("res://map2.png")
perspective.load("res://map2.png")
for px in 1:
self.texture = display
for y in map.get_height():
_y = (y + py - 1)/z
for x in map.get_width():
_x = (x + px)/z
map.lock()
pix = map.get_pixel(_x, _y)
map.unlock()
perspective.lock()
perspective.set_pixel(x, y, pix)
perspective.unlock()
display.create_from_image(perspective)
z += 1
Image:
However, I have a problem. I have the code in the ready function, in a for loop. I want it to be called every frame, but when I increase the number of repeats from one to two, it turns the entire image red. I don't know what's causing this. one guess was that I wasn't locking and unlocking the images properly, but that is most likely not the case. Another guess was that the x and y variables were not resetting each time, but that was also working fine. I don't think the loop itself is the problem, but I have no idea what's wrong.
I struggled to make your code run. I half way gave up, and implemented the logic from my prior answer using lock bits instead. This is the code:
extends Sprite
export(Transform) var matrix:Transform
var sampler:Image
var buffer:Image
var size:Vector2
var center:Vector2
func _ready():
sampler = texture.get_data()
var err = sampler.decompress()
if err != OK:
push_error("Failed to decompress texture")
return
size = Vector2(texture.get_width(), texture.get_height())
center = size * 0.5
buffer = Image.new()
buffer.create(int(size.x), int(size.y), false, Image.FORMAT_RGBA8)
func _process(_delta):
#matrix = matrix.rotated(Vector3.RIGHT, 0.01)
sampler.lock()
buffer.lock()
for y in size.x:
for x in size.y:
var uv:Vector3 = matrix * Vector3(x - center.x, y - center.y, 1.0)
if uv.z <= 0.0:
buffer.set_pixel(x, y, Color.transparent)
continue
var _x = (uv.x / uv.z) + center.x
var _y = (uv.y / uv.z) + center.y
if _x < 0.0 or _x >= size.x or _y < 0.0 or _y >= size.y:
buffer.set_pixel(x, y, Color.transparent)
continue
#buffer.set_pixel(x, y, Color(_x / size.x, y / size.y, 0.0))
buffer.set_pixel(x, y, sampler.get_pixel(_x, _y))
buffer.unlock()
sampler.unlock()
var display = ImageTexture.new()
display.create_from_image(buffer, 0)
self.texture = display
As you can see, I'm exporting a Transfrom to be available on the editor. That is a proper 3D Transform. There is a commented line on _process that does a rotation, try it out.
The sampler Image is a copy of the Texture of the Sprite (the copy is made on _ready). And the buffer Image is where what is to be displayed is constructed.
The code is creating an ImageTexture from buffer and replacing the current texture with it, each frame (on _process). I'm setting flags to 0, because FLAG_REPEAT plus FLAG_FILTER blurred the border to the opposite side of the Sprite.
The vector Vector2 size holds the size of the texture. And the Vector2 Center is the coordinates of the center.
As I said at the start, this is the logic from my prior answer. This line:
vec3 uv = matrix * vec3(UV - 0.5, 1.0);
Is equivalent to (except I'm not scaling the coordinates to the range from 0 to 1):
var uv:Vector3 = matrix * Vector3(x - center.x, y - center.y, 1.0)
Then I had this line:
if (uv.z < 0.0) discard;
Which turned out like this:
if uv.z <= 0.0:
buffer.set_pixel(x, y, Color.transparent)
continue
I'm setting transparent because I do not recreate the buffer, nor clear it before hand.
Finally this line:
COLOR = texture(TEXTURE, (uv.xy / uv.z) + 0.5);
Turned out like this:
var _x = (uv.x / uv.z) + center.x
var _y = (uv.y / uv.z) + center.y
if _x < 0.0 or _x >= size.x or _y < 0.0 or _y >= size.y:
buffer.set_pixel(x, y, Color.transparent)
continue
buffer.set_pixel(x, y, sampler.get_pixel(_x, _y))
As per the result, here is the Godot Icon "rotating in 3D" (not really, but that is the idea):
Please disregard visual artifact due to GIF encoding.
I'm not sure if you want to stay with the logic of my prior answer. However, I believe this one should not be too hard to modify for your needs.
Addendum
I used a Transform because there is no convenient Matrix type available. However, the Transform uses a Matrix internally. See also Transformation matrix.
The Mode 7 formula according to Wikipedia works with a 2 by 2 Matrix, which is simpler that what I have here. However, you are going to need the product of a Matrix and a Vector anyway. You cannot compute the components independently.
This is the formula according to Wikipedia:
r' = M*(r - r_0) + r_0
That is:
var rp = mult(M, r - r_0) + r_0
Where mult would look like this:
func mult(matrix, vector:Vector2) -> Vector2:
var x = vector.x * matrix.a + vector.y * matrix.b
var y = vector.x * matrix.c + vector.y * matrix.d
return Vector2(x, y)
However, as I said, there is no convenient matrix type. If we export a, b, c, and d, we have:
var rp = mult(a, b, c, d, r - r_0) + r_0
And mult looks like this:
func mult(a:float, b:float, c:float, d:float, vector:Vector2) -> Vector2:
var x = vector.x * a + vector.y * b
var y = vector.x * c + vector.y * d
return Vector2(x, y)
We can easily use modify the code to do that. First export a, b, c and d as I said:
export(float) var a:float
export(float) var b:float
export(float) var c:float
export(float) var d:float
And this is _process modified:
func _process(_delta):
sampler.lock()
buffer.lock()
for y in size.x:
for x in size.y:
var rp = mult(a, b, c, d, Vector2(x, y) - center) + center
if rp.x < 0.0 or rp.x >= size.x or rp.y < 0.0 or rp.y >= size.y:
buffer.set_pixel(x, y, Color.transparent)
continue
buffer.set_pixel(x, y, sampler.get_pixel(rp.x, rp.y))
buffer.unlock()
sampler.unlock()
var display = ImageTexture.new()
display.create_from_image(buffer, 6)
self.texture = display
Of course, mult is the one I showed above. I'm assuming here that r_0 is what I called center.
I'm not sure how to interpret a, b, c and d, so here is a = 1, b = 2, c = 3 and d = 4:
I am following the excism rust track, and I've hit a problem (I'm very, very new to rust)
This is a function to calculate the pythagorean triples of an integer:
use std::collections::HashSet;
use rayon::prelude::*;
pub fn find(sum: u32) -> HashSet<[u32; 3]> {
let a_b_plus_c: Vec<(u32; 2)> = (1_u32..(sum / 3_u32)).into_par_iter()
.filter_map(|a| {
let b_plus_c: u32 = sum - a;
let whole_number_check: Option<u32> = (b_plus_c.pow(2) - a.pow(2)).checked_rem(b_plus_c * 2);
match whole_number_check {
Some(0) => Some((a, b_plus_c)),
Some(_) => None,
None => None,
}
}).collect::<Vec<(u32; 2)>>();
a_b_plus_c.into_par_iter().filter_map(|a, b_plus_c| {
let b: u32 = (b_plus_c.pow(2) - a.pow(2))/(b_plus_c * 2);
let c: u32 = b_plus_c - b;
match b {
b if b > a => [a, b, c]
_ => None,
}}
).collect::<HashSet<[u32; 3]>>();
}
Or rather, it would be if it worked...
The current issue is in the line:
let a_b_plus_c: Vec<(u32; 2)> = (1_u32..(sum / 3_u32)).into_par_iter()
It says that it expected one of a number of symbols when parsing the type for a_b_plus_c, but found ;. From everything that I've seen (not much), this is the correct way to define a vector of tuples, each of which has two elements of type u32.
As I said, this is a learning exercise for me, so if anybody could help me out, I would be grateful for verbose and detailed answers :)
For what it's worth, as it might help you to comment on my code, this is the maths:
a + b + c = sum
a² + b² = c²
Rearrange for b:
b = ((b + c)² - a²) / (2(b + c))
So, iterate through a to get b+c, since (b+c) = sum - a
Then solve the above equation to get a, b+c, and b
Confirm that a < b
Then solve for c:
c = (b + c) - b
It should then spit them all out into a HashSet of arrays of a,b,c
You should enumerate each tuple's element type in definition. This should work:
let a_b_plus_c: Vec<(u32, u32)> = (1_u32..(sum / 3_u32)).into_par_iter()
I'm not sure what it means in this context. I tried adding " 'uniformoutput',false " to the end of arrayfun, but then it got upset with the "+" operator saying "Undefined operator '+' for input arguments of type 'cell'."
I changed it to ".+" but got a parse error :( What am doing wrong?
Here is an image of the part that is broken and the error. The entire code is below in case someone would like to try running it or copy the broken part.
the whole code:
function gbp2(zi,zf)
global beam xlist ylist wi qi Ri wf qf Rf Psii Psif x n
beam = struct('E',[],'lambda',[],'w',[],'R',[],'q',[],'a',[]);
E = 1; % electric field
lambda = 1064*10^-9; % wavelength
k = 2*pi/lambda; % wave number
wi = 10^-3; % initial waist width (minimum spot size)
zr = (pi*wi^2)/lambda; % Rayleigh range
Ri = zi + zr^2/zi;
qi = 1/(1/Ri-1i*lambda/(pi*wi^2)); % initial complex beam parameter
Psii = atan(real(qi)/imag(qi)); % Gouy phase
mat = [1 zf; 0 1]; % transformation matrix
A = mat(1,1); B = mat(1,2); C = mat(2,1); D = mat(2,2);
qf = (A*qi + B)/(C*qi + D);
wf = sqrt(-lambda/pi*(1/imag(1/qf)));
Rf = 1/real(1/qf);
u = #(z, coor, mode, w, R, Psi) (2/pi)^(1/4)*sqrt(exp(1i*(2*mode+1)*Psi)/(2^mode*factorial(mode)*w))*...
hermiteH(mode,sqrt(2)*coor/w)*exp(-coor^2*(1/w^2+1i*k/(2*R))-1i*k*z);
% -------------------- ERROR IN THIS PIECE (below) ----------------------------
xlist = containers.Map('KeyType','double','ValueType','any');
ylist = containers.Map('KeyType','double','ValueType','any');
function pts(z, w, R, Psi)
xlist(z) = -2*w:10^-4:2*w;
ylist(z) = zeros(1,size(xlist(z),2));
for mode = 0:2:10
ylist(z) = ylist(z) + arrayfun(#(coor) u(z, coor, mode, w, R, Psi),xlist(z),'uniformoutput',false);
end
end
pts(zi,wi,Ri,Psii)
pts(zf,wf,Rf,Psif)
plot(xlist(zi),ylist(zi),xlist(zf),ylist(zf)) end
I tried writing a similar but simpler function and it seems to work just fine:
function test(zi, zf)
u = #(z,coor,mode) z*mode + integral(#(coor)coor,0,1);
xlist = containers.Map('KeyType','double','ValueType','any');
ylist = containers.Map('KeyType','double','ValueType','any');
function pts(z)
xlist(z) = -5:5;
ylist(z) = zeros(1,size(xlist(z),2));
for mode = 0:2:10
ylist(z) = ylist(z) + arrayfun(#(coor) u(z,coor,mode),xlist(z));
end
end
pts(zi)
pts(zf)
plot(xlist(zi),ylist(zi),xlist(zf),ylist(zf))
end
so I'm not sure what the problem is with my code.
The error message give you a big hint where to look:
Undefined operator '+' for input arguments of type 'cell'.
Error in gbp2/pts (line 36)
ylist(z) = ylist(z) + arrayfun(#(coor) u(z, coor, mode, w, R,
Psi),xlist(z).','uniformoutput',false);
From the documentation for arrayfun and the 'UniformOutput' option:
Requests that the arrayfun function combine the outputs into cell arrays B1,...,Bm. The outputs of function func can be of any size or type.
Indeed, if you check, the output of this line is a cell array:
arrayfun(#(coor) u(z, coor, mode, w, R, Psi),xlist(z),'uniformoutput',false)
You can't sum the values from the cell array directly. Here's one of several ways you can do this:
v = arrayfun(#(coor) u(z, coor, mode, w, R, Psi),xlist(z),'uniformoutput',false);
ylist(z) = ylist(z) + [v{:}];
However, I don't see why you need to used the 'UniformOutput' option or even the slow arrayfun at all. Just vectorize your function with respect to coor:
u = #(z, coor, mode, w, R, Psi)(2/pi)^(1/4)*sqrt(exp(1i*(2*mode+1)*Psi)/(2^mode*factorial(mode)*w))*...
hermiteH(mode,sqrt(2)*coor/w).*exp(-coor.^2*(1/w^2+1i*k/(2*R))-1i*k*z);
Now
ylist(z) = ylist(z) + u(z, xlist(z), mode, w, R, Psi);
Some additional suggestions: Don't use global variables – they're inefficient and there are almost always better solutions. If pts is meant to be a nested function, you're missing a closing end for the main gbp2 function. It might be a good idea to rename your variable mode so that it doesn't overload the built-in function of the same name. Psif isn't defined. And zeros(1,size(xlist(z),2)) can be written simply as zeros(size(xlist(z))).
I followed this link
Passing a data frame from-to R and C using .call()
to find the way to access an R data frame inside C.
My requirement is the opposite of that. I have a tabular data in C and need to create an R data frame object in C and return it on as SEXP.
For simple R vectors and lists creation, I followed something like in this link
http://adv-r.had.co.nz/C-interface.html
But I am still wondering how to create a dataframe and return from C to R. Considering a dataframe is a list, I tried creating a list and passing it on, but it expectedly gets me a list in R and not a dataframe.
Any help would be appreciated.
You may make use of the fact that a data.frame object is a list consisting of atomic vectors, each having the same length, with names, class, and row.names attributes properly set:
library(inline)
f <- cxxfunction(signature(), body='
SEXP ret, ans1, ans2, cls, nam, rownam;
PROTECT(ret = Rf_allocVector(VECSXP, 2)); // a list with two elements
PROTECT(ans1 = Rf_allocVector(INTSXP, 3)); // first column
PROTECT(ans2 = Rf_allocVector(INTSXP, 3)); // second column
for (int i=0; i<3; ++i) { // some data
INTEGER(ans1)[i] = i+1;
INTEGER(ans2)[i] = -(i+1);
}
SET_VECTOR_ELT(ret, 0, ans1);
SET_VECTOR_ELT(ret, 1, ans2);
PROTECT(cls = allocVector(STRSXP, 1)); // class attribute
SET_STRING_ELT(cls, 0, mkChar("data.frame"));
classgets(ret, cls);
PROTECT(nam = allocVector(STRSXP, 2)); // names attribute (column names)
SET_STRING_ELT(nam, 0, mkChar("a"));
SET_STRING_ELT(nam, 1, mkChar("b"));
namesgets(ret, nam);
PROTECT(rownam = allocVector(STRSXP, 3)); // row.names attribute
SET_STRING_ELT(rownam, 0, mkChar("1"));
SET_STRING_ELT(rownam, 1, mkChar("2"));
SET_STRING_ELT(rownam, 2, mkChar("3"));
setAttrib(ret, R_RowNamesSymbol, rownam);
UNPROTECT(6);
return ret;
')
Which yields:
print(f())
## a b
## 1 1 -1
## 2 2 -2
## 3 3 -3
Obligatory Rcpp example:
// [[Rcpp::export]]
DataFrame createTwo(){
IntegerVector v = IntegerVector::create(1,2,3);
std::vector<std::string> s(3);
s[0] = "a";
s[1] = "b";
s[2] = "c";
return DataFrame::create(Named("a")=v, Named("b")=s);
}
which will get you a 3x2 data.frame with one char vector and one int vector.
Hey guyz. Can help me on this?
if size(cost,1) == 2
A = (4*Pdt*cost(1,3)*cost(2,3)) + 2*(cost(1,2)*cost(2,3))+(cost(1,3)*cost(2,2));
B = 2*(cost(2,3)+cost(1,3));
lambda = num2str(A ./ B);
set(handles.answer1_staticText,'String', lambda);
P1 = (lambda - cost(1,2))./(2*cost(1,3));
P2 = (lambda - cost(2,2))./(2*cost(2,3));
PT = mat2str(P1 + P2);
set(handles.answer2_staticText,'String', PT);
guidata(hObject, handles);
end
From the coding above, the answer become like this :
[11.75 11.25 11.25 11.75 10.75 11.5 12.75 12.75 13]
My question is I want to display my answer at the static text box like this:
P1 = (%answer for P1)
P2 = (%answer for P2)
P TOTAL = (%answer for PT)
Can anyone help me with the coding?
You have converted lambda to a string (using num2str), and thus, the calculation of P1 etc will produce unexpected results.
It's better to only convert to string in the display step, so these accidents won't happen.
Try this:
if size(cost,1) == 2
A = (4*Pdt*cost(1,3)*cost(2,3)) + 2*(cost(1,2)*cost(2,3))+(cost(1,3)*cost(2,2));
B = 2*(cost(2,3)+cost(1,3));
lambda = A ./ B;
set(handles.answer1_staticText,'String', num2str(lambda));
P1 = (lambda - cost(1,2))./(2*cost(1,3));
P2 = (lambda - cost(2,2))./(2*cost(2,3));
PT = P1 + P2;
set(handles.answer2_staticText,'String', num2str(PT));
guidata(hObject, handles);
end