小白上完第一节课有一堆问题想问

胡大佬说这节课0到99岁任何基础的人都能学,有学过高数最好,但没学过也没关系,所以我就来了。先说一下我的知识水平吧,学过三个月Python,数学和物理都是高中文科水平(现在忘了不少东西,所以估计连高中文科都没有了)。现在读本科大二,因为专业和数学没有任何关系所以根本没学高数,也没学过线性代数,数学课我选的是Math for Liberal Arts。

下面我整理了一些我听完第一节课后搞不清楚的问题:

  1. 32位数和64位数的区别是什么?
    整数和浮点数都有这个32和64位的分别,那具体区别在哪里?什么时候用哪个?我只知道电脑64位系统比32位好,好在哪里我也不知道,也不知道和这个有没有联系。查了一下资料,说64位能用的数字更多,但是这么大的数字一般用不上吧?那一般来说两个是一样的吗?

  2. 矩阵是什么?张量又是什么?
    在这节课前我根本没有听过这两个词,胡大佬讲的时候也默认大家明白这两个是啥了,所以我听得一脸懵,查了很多资料也没看懂。现在我的理解是这样的,不知道有没有弄错:矩阵就是表格,太极的张量没有数学里那么复杂,其实就是更大型的表格。这样理解对吗?
    然后是具体的代码,直播里有一个这样的例子:
    a = ti.var(dt=ti.f32, shape=42, 63)
    b = ti.Vector(3, dt=ti.f32, shape=4)
    c = ti.Matrix(2, 2, dt=ti.f32, shape=(3, 5))
    b刚开头的3,胡大佬说是三维的向量所以写3。我试了试,好像把这个3删掉后,程序运行也没有报错。那这个3不一定要写,只是给自己看的吗?不写的话它会默认什么数字呢?同理c开头的2, 2我试了也是删了也没报错,如果不写,它默认是算多少?还有c开头的2, 2我只写一个2运行也不报错,如果只写一个数字他是怎么算的?a的shape=42, 63我试了试,只写一个数他也没报错,那这个又是怎么算的?我把a b c的shape全部删掉也没有报错,那在没有shape的时候它是怎么算的?

还有a和c的shape,比如c的是3乘5,那这个3和5有没有被包括进去?因为后边讲struct for循环时有个例子,一个640*320的张量却最后一个坐标只有(639, 319),所以想问一下。

  1. 后边讲range for循环时有一个例子。
    @ti.kernel
    def fill():
    for i in range(10):
    x[i] += i

     s = 0
     for j in range(5):
         s += j
    
     y[i] = s
    

这里面的x是哪里来的?y又是哪里来的?是不是应该是def fill(x, y)?
由于连xy是什么都不明白,我也没搞懂这个叫fill的function到底是干嘛用的。

后面的struct for loop 其实也没看懂,但这个不懂的很彻底,彻底到我不知怎么问…

  1. 关于@ti.function的问题

直播时有一个例子是这样的
@ti.func
def triple(x):
return x * 3

然后我在后面加了一个
print(triple(5))
结果print出来是这样的
<taichi.lang.expr.Expr object at 0x0000022F946B40A0>
这是什么鬼?我该怎么正常地print它出来?@ti.kernel我试了一下,是可以直接这样print出来的,为什么@ti.func不行呢?

作为曾经的化学僧物理研究僧,到现在的无业游民,我自认为困扰萌新使用taichi的主要的问题:
1、计算机基础薄弱及不了计算机内部结构,建议用半个小时时间翻阅一下《大学计算机基础》并咸鱼80块收一台五脏俱全的古董机用于拆解学习。
2、关于线性代数,数学相关多少是要会一点的,从零开始的话建议先翻阅《高等数学上册》以及《线性代数基础》的前四章。
3、关于编程语言,要认识到一个问题,taichi和Python是两个独立的语言,建议先github搜索Python-100-Days用一个下午左右的时间浏览前80days,零基础理解不了代码的情况下也建议浏览,要在遇到问题时知道有能参考的代码,在能基本运用python的情况下,再学习taichi,这样有助于理解taichi的使用逻辑。

狗头狗头狗头_你的问题在课本上能获得准确且专业的解答 :joy:

4 个赞

谢谢这些书本的推荐。:sweat_smile: 我只是想要某些特定问题的,针对太极的答案,并不一定要完全理解,比如张量,我只需理解到能正常使用太极里的张量的地步就行了,所以我才来这里问。另外我在帖子里说了我学过三个月的Python(而且还是在学校里专门报了节课学的),基本的print, if, for, while, def 之类的还是能理解的,但确实再深一丢丢就有点吃力了,的确需要继续深入学习。你特地强调太极和Python是不一样的,是不是叫我不要用Python的print?太极里是有另一个和print差不多用途的指令吗?

  1. 如果你在@ti.kernel调用这个func行不行?
1 个赞

那具体应该怎样做呢?我试过在@ti.func前面加@ti.kernel,报错了;在print前面加@ti.kernel也报错了(另外这样搞的时候,发现@ti.kernel后面貌似一定要加def否则无意义,不知道有没有弄错)

import taichi as ti

@ti.func
def printstuff(v):
  print(v)

@ti.kernel
def sample():
  v = ti.Vector([1.2, 2.4])
  printstuff(v)

sample()
  1. 对于整数来说,32位和64位只有能够表达数字大小的差别,所以一般来说,32位够用了;对于浮点数来说,除了表达数字大小的差别,还有一个差别就在于精度上,因为64位能够用来表示浮点数小数位的位数更多,所以会比32位的更精确。

  2. 矩阵和张量在太极里面的区别在于,矩阵的元素只能是数字,而张量的元素除了可以是数字还可以是矩阵,当然,它同时也像你理解的,是更大型的表格,更高维度的表格;

不输入Vector的第一个参数,即向量里标量的个数,它默认就是一维的向量,即和你用ti.Var是等价的;同理,只输入Matrix前两个参数中的一个,它默认就是一个n*1的矩阵或者说向量,和你用Vector是等价的,前两个参数都不输入,其实就和ti.Var是等价的;

关于shape这个参数,它指定的是你申请的张量的大小,这部分推荐你看一下taichi的文档:标量组成的张量。你不指定shape这个参数并没有什么问题,只不过后续需要一个放置操作(place),具体的你可以看看文档;而你指定的shape是42还是(42, 63),这决定了张量是42维的还是42*63的,所以都可以的,你还可以写加上更多数字,表示更高维度的张量;

另外,你a = ti.var(dt=ti.f32, shape=42, 63)应该是少打了一个括号,应该为a = ti.var(dt=ti.f32, shape=(42, 63));

python的下标是从0开始的,所以最后一个坐标会比实际的大小少1

3 个赞

32/64 的区别就跟你一只手能数 5 个数,两只手能数 10 个数一样,占用的位数多了,能表示的范围也更大。(如果你的手足够灵活 一只手其实能数 2^5==32个数)

具体的范围、浮点数的精度搜一搜就知道了。

建议都用 32 位的,为了兼容性。

CPU/CUDA OpenGL Metal 均兼容 32 位, 64 位就不一定了
ref:文档末尾 原子操作 — taichi 0.6.5 文档


这样理解挺好的。

你把张量也看成表格就行了。
我们说的标量、向量、矩阵,都指的是表格的格子里放的东西。

表格里可以放

以上三条的 shape 指的是张量,也就是表格的维数。
dt 是 dataType / 数据类型的简写。

值得注意的点

向量是只有一列的特殊矩阵。实际上, ti.Vector 只是 ti.Matrix 的别名。

声明一个 ti.Matrix(64, 32, dt=ti.f32, shape=(3, 2)) 是不合理的,
可以试着用 ti.Matrix(3, 2, dt=ti.f32, shape=(64, 32)) 代替
——始终把大的维度放在张量里。


这个是例子没写全。
这里的 x, y 应该是外面声明的全局变量。
这里只是为了说明 kernel 的第一个循环会自动并行,里面的不会。所以只写了一部分代码。


@ti.func 只能在 kernel 里调用, kernel 才能在 python 环境中调用。
这个上课提到过。

2 个赞

感谢几位大神解答,我先消化消化 :laughing:

搞明白了,感谢各路大佬 :pray:
顺便把我的4的解决办法发在这里

import taichi as ti
ti.init()


@ti.func
def triple(x: ti.i32) -> ti.i32:
    printed_triple = x * 3
    return printed_triple


@ti.kernel
def print_triple(x: ti.i32) -> ti.i32:
    print(triple(x))
    return triple(x)


print_triple(5)